mirror of
https://git.savannah.gnu.org/git/emacs/org-mode.git
synced 2024-08-26 14:32:52 +00:00
TODO statistics: Allow recursive statistics
Setting the new option `org-hierarchical-todo-statistics' to nil will make TODO statistics to be computed recursively. This means, not only the direct children of a node contribute to its TODO statistics, but the entire subtree. You can also set the COOKIE_DATA property and add the word "recursive" there to get recursive statistics for a specific tree.
This commit is contained in:
parent
83e82f9ccd
commit
f54ff074d2
|
@ -1,3 +1,12 @@
|
||||||
|
2009-05-20 Carsten Dominik <carsten.dominik@gmail.com>
|
||||||
|
|
||||||
|
* org-list.el (org-update-checkbox-count): Make property
|
||||||
|
dependent.
|
||||||
|
|
||||||
|
* org.el (org-hierarchical-todo-statistics): New option.
|
||||||
|
(org-update-parent-todo-statistics): Modified to handle recursive
|
||||||
|
statistics.
|
||||||
|
|
||||||
2009-05-19 Carsten Dominik <carsten.dominik@gmail.com>
|
2009-05-19 Carsten Dominik <carsten.dominik@gmail.com>
|
||||||
|
|
||||||
* org-publish.el (org-publish): Make this function behave
|
* org-publish.el (org-publish): Make this function behave
|
||||||
|
|
|
@ -393,6 +393,10 @@ the whole buffer."
|
||||||
(re-find (concat re "\\|" re-box))
|
(re-find (concat re "\\|" re-box))
|
||||||
beg-cookie end-cookie is-percent c-on c-off lim
|
beg-cookie end-cookie is-percent c-on c-off lim
|
||||||
eline curr-ind next-ind continue-from startsearch
|
eline curr-ind next-ind continue-from startsearch
|
||||||
|
(recursive
|
||||||
|
(or (not org-hierarchical-checkbox-statistics)
|
||||||
|
(string-match "\\<recursive\\>"
|
||||||
|
(or (org-entry-get nil "COOKIE_DATA") ""))))
|
||||||
(cstat 0)
|
(cstat 0)
|
||||||
)
|
)
|
||||||
(when all
|
(when all
|
||||||
|
@ -404,12 +408,11 @@ the whole buffer."
|
||||||
(while (and (re-search-backward re-find beg t)
|
(while (and (re-search-backward re-find beg t)
|
||||||
(not (save-match-data
|
(not (save-match-data
|
||||||
(and (org-on-heading-p)
|
(and (org-on-heading-p)
|
||||||
|
(string-match "\\<todo\\>"
|
||||||
(equal (downcase
|
(downcase
|
||||||
(or (org-entry-get
|
(or (org-entry-get
|
||||||
nil "COOKIE_DATA")
|
nil "COOKIE_DATA")
|
||||||
""))
|
"")))))))
|
||||||
"todo")))))
|
|
||||||
(setq beg-cookie (match-beginning 1)
|
(setq beg-cookie (match-beginning 1)
|
||||||
end-cookie (match-end 1)
|
end-cookie (match-end 1)
|
||||||
cstat (+ cstat (if end-cookie 1 0))
|
cstat (+ cstat (if end-cookie 1 0))
|
||||||
|
@ -432,9 +435,9 @@ the whole buffer."
|
||||||
(setq curr-ind (org-get-indentation))
|
(setq curr-ind (org-get-indentation))
|
||||||
(setq next-ind curr-ind)
|
(setq next-ind curr-ind)
|
||||||
(while (and (bolp) (org-at-item-p)
|
(while (and (bolp) (org-at-item-p)
|
||||||
(if org-hierarchical-checkbox-statistics
|
(if recursive
|
||||||
(= curr-ind next-ind)
|
(<= curr-ind next-ind)
|
||||||
(<= curr-ind next-ind)))
|
(= curr-ind next-ind)))
|
||||||
(save-excursion (end-of-line) (setq eline (point)))
|
(save-excursion (end-of-line) (setq eline (point)))
|
||||||
(if (re-search-forward re-box eline t)
|
(if (re-search-forward re-box eline t)
|
||||||
(if (member (match-string 2) '("[ ]" "[-]"))
|
(if (member (match-string 2) '("[ ]" "[-]"))
|
||||||
|
@ -442,7 +445,7 @@ the whole buffer."
|
||||||
(setq c-on (1+ c-on))
|
(setq c-on (1+ c-on))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(if org-hierarchical-checkbox-statistics
|
(if (not recursive)
|
||||||
(org-end-of-item)
|
(org-end-of-item)
|
||||||
(end-of-line)
|
(end-of-line)
|
||||||
(when (re-search-forward org-list-beginning-re lim t)
|
(when (re-search-forward org-list-beginning-re lim t)
|
||||||
|
|
85
lisp/org.el
85
lisp/org.el
|
@ -1737,6 +1737,13 @@ entry each time a todo state is changed."
|
||||||
:group 'org-todo
|
:group 'org-todo
|
||||||
:type 'boolean)
|
:type 'boolean)
|
||||||
|
|
||||||
|
(defcustom org-hierarchical-todo-statistics t
|
||||||
|
"Non-nil means, TODO statistics covers just direct children.
|
||||||
|
When nil, all entries in the subtree are considered.
|
||||||
|
This has only an effect if `org-provide-todo-statistics' is set."
|
||||||
|
:group 'org-todo
|
||||||
|
:type 'boolean)
|
||||||
|
|
||||||
(defcustom org-after-todo-state-change-hook nil
|
(defcustom org-after-todo-state-change-hook nil
|
||||||
"Hook which is run after the state of a TODO item was changed.
|
"Hook which is run after the state of a TODO item was changed.
|
||||||
The new state (a string with a TODO keyword, or nil) is available in the
|
The new state (a string with a TODO keyword, or nil) is available in the
|
||||||
|
@ -9442,37 +9449,59 @@ changes because there are uncheckd boxes in this entry."
|
||||||
t)) ; do not block
|
t)) ; do not block
|
||||||
|
|
||||||
(defun org-update-parent-todo-statistics ()
|
(defun org-update-parent-todo-statistics ()
|
||||||
"Update any statistics cookie in the parent of the current headline."
|
"Update any statistics cookie in the parent of the current headline.
|
||||||
|
When `org-hierarchical-todo-statistics' is nil, statistics will cover
|
||||||
|
the entire subtree and this will travel up the hierarchy and update
|
||||||
|
statistics everywhere."
|
||||||
(interactive)
|
(interactive)
|
||||||
(let ((box-re "\\(\\(\\[[0-9]*%\\]\\)\\|\\(\\[[0-9]*/[0-9]*\\]\\)\\)")
|
(let* ((lim 0) prop
|
||||||
level (cnt-all 0) (cnt-done 0) is-percent kwd cookie-present)
|
(recursive (or (not org-hierarchical-todo-statistics)
|
||||||
|
(string-match
|
||||||
|
"\\<recursive\\>"
|
||||||
|
(or (setq prop (org-entry-get
|
||||||
|
nil "COOKIE_DATA" 'inherit)) ""))))
|
||||||
|
(lim (or (and prop (marker-position
|
||||||
|
org-entry-property-inherited-from))
|
||||||
|
lim))
|
||||||
|
(first t)
|
||||||
|
(box-re "\\(\\(\\[[0-9]*%\\]\\)\\|\\(\\[[0-9]*/[0-9]*\\]\\)\\)")
|
||||||
|
level ltoggle l1
|
||||||
|
(cnt-all 0) (cnt-done 0) is-percent kwd cookie-present)
|
||||||
(catch 'exit
|
(catch 'exit
|
||||||
(save-excursion
|
(save-excursion
|
||||||
(setq level (org-up-heading-safe))
|
(beginning-of-line 1)
|
||||||
(unless (and level
|
(if (org-at-heading-p)
|
||||||
(not (equal (downcase
|
(setq ltoggle (funcall outline-level))
|
||||||
(or (org-entry-get
|
(error "This should not happen"))
|
||||||
nil "COOKIE_DATA")
|
(while (and (setq level (org-up-heading-safe))
|
||||||
""))
|
(or recursive first)
|
||||||
"checkbox")))
|
(>= (point) lim))
|
||||||
(throw 'exit nil))
|
(setq first nil)
|
||||||
(while (re-search-forward box-re (point-at-eol) t)
|
(unless (and level
|
||||||
(setq cnt-all 0 cnt-done 0 cookie-present t)
|
(not (string-match
|
||||||
(setq is-percent (match-end 2))
|
"\\<checkbox\\>"
|
||||||
(save-match-data
|
(downcase
|
||||||
(unless (outline-next-heading) (throw 'exit nil))
|
(or (org-entry-get
|
||||||
(while (looking-at org-todo-line-regexp)
|
nil "COOKIE_DATA")
|
||||||
(setq kwd (match-string 2))
|
"")))))
|
||||||
(and kwd (setq cnt-all (1+ cnt-all)))
|
(throw 'exit nil))
|
||||||
(and (member kwd org-done-keywords)
|
(while (re-search-forward box-re (point-at-eol) t)
|
||||||
(setq cnt-done (1+ cnt-done)))
|
(setq cnt-all 0 cnt-done 0 cookie-present t)
|
||||||
(condition-case nil
|
(setq is-percent (match-end 2))
|
||||||
(org-forward-same-level 1)
|
(save-match-data
|
||||||
(error (end-of-line 1)))))
|
(unless (outline-next-heading) (throw 'exit nil))
|
||||||
(replace-match
|
(while (and (looking-at org-complex-heading-regexp)
|
||||||
(if is-percent
|
(> (setq l1 (length (match-string 1))) level))
|
||||||
(format "[%d%%]" (/ (* 100 cnt-done) (max 1 cnt-all)))
|
(setq kwd (and (or recursive (= l1 ltoggle))
|
||||||
(format "[%d/%d]" cnt-done cnt-all))))
|
(match-string 2)))
|
||||||
|
(and kwd (setq cnt-all (1+ cnt-all)))
|
||||||
|
(and (member kwd org-done-keywords)
|
||||||
|
(setq cnt-done (1+ cnt-done)))
|
||||||
|
(outline-next-heading)))
|
||||||
|
(replace-match
|
||||||
|
(if is-percent
|
||||||
|
(format "[%d%%]" (/ (* 100 cnt-done) (max 1 cnt-all)))
|
||||||
|
(format "[%d/%d]" cnt-done cnt-all)))))
|
||||||
(when cookie-present
|
(when cookie-present
|
||||||
(run-hook-with-args 'org-after-todo-statistics-hook
|
(run-hook-with-args 'org-after-todo-statistics-hook
|
||||||
cnt-done (- cnt-all cnt-done)))))
|
cnt-done (- cnt-all cnt-done)))))
|
||||||
|
|
Loading…
Reference in a new issue