summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBastien <bzg@gnu.org>2020-02-14 10:32:35 +0100
committerBastien <bzg@gnu.org>2020-02-14 10:32:35 +0100
commit27e4d7ce487b38428618ed1fb2a6e2a1b59098bc (patch)
tree6460679d7cb066dbcc8a52e36784af2376265b76
parent29f44df758d182873c9241f3cb202968b410f0bd (diff)
downloadorg-mode-27e4d7ce487b38428618ed1fb2a6e2a1b59098bc.tar.gz
Prevent infinite loop when showing new time in agenda
* lisp/org-agenda.el (org-agenda-dim-blocked-tasks): Don't use an overlay to make the task invisible, use text properties. (org-agenda--mark-blocked-entry): Add text property 'org-filter-type to later use `org-agenda-filter-hide-line' if necessary. (org-agenda-filter-hide-line): Fix docstring. The related bug was first reported in 2013 by Matt Lundin here: https://lists.gnu.org/archive/html/emacs-orgmode/2013-08/msg00072.html Then Andrew Hyatt reported it again, and provided a minimal recipe on how to reproduce it consistently. Thanks a lot to both of them.
-rw-r--r--lisp/org-agenda.el32
1 files changed, 19 insertions, 13 deletions
diff --git a/lisp/org-agenda.el b/lisp/org-agenda.el
index aed1b24..ec12710 100644
--- a/lisp/org-agenda.el
+++ b/lisp/org-agenda.el
@@ -4003,7 +4003,7 @@ dimming them."
(when (called-interactively-p 'interactive)
(message "Dim or hide blocked tasks..."))
(dolist (o (overlays-in (point-min) (point-max)))
- (when (eq (overlay-get o 'org-type) 'org-blocked-todo)
+ (when (eq (overlay-get o 'face) 'org-agenda-dimmed-todo-face)
(delete-overlay o)))
(save-excursion
(let ((inhibit-read-only t))
@@ -4011,22 +4011,26 @@ dimming them."
(while (let ((pos (text-property-not-all
(point) (point-max) 'org-todo-blocked nil)))
(when pos (goto-char pos)))
- (let* ((invisible (eq (org-get-at-bol 'org-todo-blocked) 'invisible))
+ (let* ((invisible
+ (eq (org-get-at-bol 'org-todo-blocked) 'invisible))
+ (todo-blocked
+ (eq (org-get-at-bol 'org-filter-type) 'todo-blocked))
(ov (make-overlay (if invisible
(line-end-position 0)
(line-beginning-position))
(line-end-position))))
- (if invisible
- (overlay-put ov 'invisible t)
+ (when todo-blocked
(overlay-put ov 'face 'org-agenda-dimmed-todo-face))
- (overlay-put ov 'org-type 'org-blocked-todo))
- (forward-line))))
+ (when invisible
+ (org-agenda-filter-hide-line 'todo-blocked)))
+ (move-beginning-of-line 2))))
(when (called-interactively-p 'interactive)
(message "Dim or hide blocked tasks...done")))
(defun org-agenda--mark-blocked-entry (entry)
- "For ENTRY a string with the text property `org-hd-marker', if
-the header at `org-hd-marker' is blocked according to
+ "If ENTRY is blocked, mark it for fontification or invisibility.
+
+If the header at `org-hd-marker' is blocked according to
`org-entry-blocked-p', then if `org-agenda-dim-blocked-tasks' is
'invisible and the header is not blocked by checkboxes, set the
text property `org-todo-blocked' to `invisible', otherwise set it
@@ -4050,7 +4054,9 @@ to t."
(put-text-property
0 (length entry) 'org-todo-blocked
(if really-invisible 'invisible t)
- entry)))))))
+ entry)
+ (put-text-property
+ 0 (length entry) 'org-filter-type 'todo-blocked entry)))))))
entry)
(defvar org-agenda-skip-function nil
@@ -8064,13 +8070,13 @@ tags in the FILTER if any of the tags in FILTER are grouptags."
org-agenda-filtered-by-top-headline t))
(defun org-agenda-filter-hide-line (type)
- "Hide lines with TYPE in the agenda buffer."
+ "If current line is TYPE, hide it in the agenda buffer."
(let* (buffer-invisibility-spec
- (b (max (point-min) (1- (point-at-bol))))
- (e (point-at-eol)))
+ (beg (max (point-min) (1- (point-at-bol))))
+ (end (point-at-eol)))
(let ((inhibit-read-only t))
(add-text-properties
- b e `(invisible org-filtered org-filter-type ,type)))))
+ beg end `(invisible org-filtered org-filter-type ,type)))))
(defun org-agenda-remove-filter (type)
(interactive)