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

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

[elpa] externals/org f9702a09e7 2/2: org-fold: Fix edge case when reveal


From: ELPA Syncer
Subject: [elpa] externals/org f9702a09e7 2/2: org-fold: Fix edge case when revealing fragile folds breaks some Emacs commands
Date: Tue, 9 Jan 2024 12:58:23 -0500 (EST)

branch: externals/org
commit f9702a09e79da6fbb0e3e3d01b0e2e1145c2e70f
Author: Ihor Radchenko <yantar92@posteo.net>
Commit: Ihor Radchenko <yantar92@posteo.net>

    org-fold: Fix edge case when revealing fragile folds breaks some Emacs 
commands
    
    * lisp/org-fold-core.el (org-fold-core--fix-folded-region): Delay
    revealing fragile regions to until the current command is executed.
    (org-fold-core--region-delayed): New function to postpone folding to
    the time when `post-command-hook' is executed.
    (org-fold-core--region-delayed-list): New internal variable holding
    delayed fold requests.
    (org-fold-core--process-delayed): New function to be used to process
    the delayed folds and cleanup `post-command-hook'.
    *
    testing/lisp/test-org-fold.el 
(test-org-fold/org-fold-reveal-broken-structure):
    Update tests to account for the delayed unfolding.
    
    Reported-by: Sebastian Miele <iota@whxvd.name>
    Link: https://orgmode.org/list/875y04yq9s.fsf@localhost
---
 lisp/org-fold-core.el         | 32 +++++++++++++++++++++++++++++++-
 testing/lisp/test-org-fold.el |  5 +++++
 2 files changed, 36 insertions(+), 1 deletion(-)

diff --git a/lisp/org-fold-core.el b/lisp/org-fold-core.el
index 3f5bd2121b..11de2bff61 100644
--- a/lisp/org-fold-core.el
+++ b/lisp/org-fold-core.el
@@ -1311,6 +1311,33 @@ instead of text properties.  The created overlays will 
be stored in
   `(let ((org-fold-core--ignore-fragility-checks t))
      (progn ,@body)))
 
+(defvar org-fold-core--region-delayed-list nil
+  "List holding (MKFROM MKTO FLAG SPEC-OR-ALIAS) arguments to process.
+The list is used by `org-fold-core--region-delayed'.")
+(defun org-fold-core--region-delayed (from to flag &optional spec-or-alias)
+  "Call `org-fold-core-region' after current command.
+Pass the same FROM, TO, FLAG, and SPEC-OR-ALIAS."
+  ;; Setup delayed folding.
+  (add-hook 'post-command-hook #'org-fold-core--process-delayed)
+  (let ((frommk (make-marker))
+        (tomk (make-marker)))
+    (set-marker frommk from (current-buffer))
+    (set-marker tomk to (current-buffer))
+    (push (list frommk tomk flag spec-or-alias) 
org-fold-core--region-delayed-list)))
+
+(defun org-fold-core--process-delayed ()
+  "Perform folding for `org-fold-core--region-delayed-list'."
+  (when org-fold-core--region-delayed-list
+    (mapc (lambda (args)
+            (when (< (nth 0 args) (nth 1 args))
+              (org-with-point-at (car args)
+                (apply #'org-fold-core-region args))))
+          ;; Restore the initial folding order.
+          (nreverse org-fold-core--region-delayed-list))
+    ;; Cleanup `post-command-hook'.
+    (remove-hook 'post-command-hook #'org-fold-core--process-delayed)
+    (setq org-fold-core--region-delayed-list nil)))
+
 (defvar-local org-fold-core--last-buffer-chars-modified-tick nil
   "Variable storing the last return value of `buffer-chars-modified-tick'.")
 
@@ -1428,7 +1455,10 @@ property, unfold the region if the :fragile function 
returns non-nil."
                                             (cons fold-begin fold-end)
                                             spec))
                              ;; Reveal completely, not just from the SPEC.
-                             (org-fold-core-region fold-begin fold-end nil)))))
+                             ;; Do it only after command is finished -
+                             ;; some Emacs commands assume that
+                             ;; visibility is not altered by 
`after-change-functions'.
+                             (org-fold-core--region-delayed fold-begin 
fold-end nil)))))
                      ;; Move to next fold.
                      (setq pos (org-fold-core-next-folding-state-change spec 
pos local-to)))))))))))))
 
diff --git a/testing/lisp/test-org-fold.el b/testing/lisp/test-org-fold.el
index 22f17977f1..9f15f0a383 100644
--- a/testing/lisp/test-org-fold.el
+++ b/testing/lisp/test-org-fold.el
@@ -469,6 +469,7 @@ Text here"
       (should (org-invisible-p))
       (goto-char 1)
       (org-delete-char 1)
+      (run-hooks 'post-command-hook)
       (re-search-forward "Text")
       (should-not (org-invisible-p)))
     (org-test-with-temp-text
@@ -480,6 +481,7 @@ Text here"
       (goto-char 1)
       (let ((last-command-event ?a))
         (org-self-insert-command 1))
+      (run-hooks 'post-command-hook)
       (re-search-forward "Text")
       (should-not (org-invisible-p)))
     (org-test-with-temp-text
@@ -494,6 +496,7 @@ Text here"
       (should (org-invisible-p))
       (re-search-backward ":PROPERTIES:")
       (delete-char 1)
+      (run-hooks 'post-command-hook)
       (re-search-forward "ID")
       (should-not (org-invisible-p)))
     (org-test-with-temp-text
@@ -508,6 +511,7 @@ Text here"
       (should (org-invisible-p))
       (re-search-forward ":END:")
       (delete-char -1)
+      (run-hooks 'post-command-hook)
       (re-search-backward "ID")
       (should-not (org-invisible-p)))
     (org-test-with-temp-text
@@ -521,6 +525,7 @@ Text here"
       (re-search-forward "end")
       (should (org-invisible-p))
       (delete-char -1)
+      (run-hooks 'post-command-hook)
       (re-search-backward "2")
       (should-not (org-invisible-p)))))
 



reply via email to

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