emacs-orgmode@gnu.org archives
 help / color / mirror / code / Atom feed
* [CODE] Stuck projects and unbacked priorities
@ 2011-02-27  7:11 Marc-Oliver Ihm
  0 siblings, 0 replies; only message in thread
From: Marc-Oliver Ihm @ 2011-02-27  7:11 UTC (permalink / raw)
  To: emacs-orgmode

Hello,

I would like to offer some code to find *unbacked priorities* in ones 
projects. Let me explain.

It is well known, that orgmode supports (but does not enforce) David
Allens GTD-approach. One aspect of this approach is to make sure, that
every project (which translates to a toplevel TODO-entry in orgmode),
has at least one subentry in state NEXT.

Now, if someone tries to advance his projects, he simply draws one of
those NEXT-entries and starts to work on it. And of course, this is
supported by orgmode, which makes it very easy to generate such a list
of NEXT-entries as part of a custom agenda.

This is how I, and probably many more people, do their daily work.

However things are not so clear, if one tries to work with priorities
too. Probably one would try to assign priorities (lets say "A" to "D")
to projects (i.e. toplevel TODO-entries); but those priorities (assigned
to TODO-entries) are not visible in the list of NEXT-entries, which is
the basis for daily work.

Inheritance would be an option, giving each NEXT-entry the priority of
its parent TODO-entry; that however would give the same priority to
*all* NEXT-entries within a given project, making it impossible to
differentiate between them. And if a project has many NEXT-entries, than
each one would have the same priority.

So (in my opinion) one needs to assign individual priorities to each
NEXT-entry, or at least to one of them. This priority assigned to the
NEXT-entry should then not be less than the priority of its project (the
toplevel TODO-entry), because if the project is important, than it
should be important too, to work on one of its pieces.

This check ("Is there any project, which has no NEXT-entries of equal
priority ?") is done by the function "org-unbacked-priorities", which
you find below and which I would like to present here for discussion.

A small example. Lets assume that you have two projects (project 1 and
2), each with some NEXT-entries (task 1 to 5):

* TODO [#A] project 1
** NEXT [#A] task 1
** NEXT [#B] task 2
* TODO [#B] project 2
** NEXT [#C] task 3
** NEXT [#D] task 4
** WAIT task 5

Now, you may see, that neither of these two projects is stuck, because
they both have NEXT-entries ready to be worked upon.

Project 2 however, has (as I would like to call it) an
*unbacked priority*: The project itself has priority "B", but none of
its NEXT-entries matches this overall priority; the highest ranking
entry is task 3 with priority of only "C".

To spot such a situation, one could use the function "org-unbacked
priorities". For the given example it would produce a list with project
2 as a single entry:

* TODO [#B] project 2

With such a list, one could then decide, either to increase the priority
of a NEXT-entry (lets say from "C" to "B") or (just the other way
around) to decrease the overall priority of project 2 from "B" to "C".

Okay, I hope, that describes the case. Please find the named function
below. Currently it is far from perfect and has no options to be
customized (and takes no arguments either). However, if people think it
could be useful, I would be grateful for any suggestions for improvements.


with kind regards, Marc-Oliver Ihm



(defun org-unbacked-priorities ()
   "Find toplevel entries, that do not have at least one child in state 
NEXT and of priority equal or higher"
   (interactive)
   (let ((level-1-prio 0)
         (level-other-highest-prio 0)
         level-1-heading
         level-1-state
         level-1-marker
         insert-helper
         result-buffer)

     (setq result-buffer (get-buffer-create "*Unbacked priorities*"))
     (save-excursion (set-buffer result-buffer)
                     (erase-buffer)
                     (insert "These TODO-entries have a higher priority 
than any of its subentries\nin state NEXT (or they have no such 
subentry).\n\n")
                     )

     (setq insert-helper (lambda ()
                           (when (and
                                  (string= level-1-state "TODO")
                                  (< level-other-highest-prio level-1-prio))
                             (org-add-props level-1-heading nil 
'org-marker level-1-marker)
                             (save-excursion
                               (set-buffer result-buffer)
                               (end-of-buffer)
                               (insert level-1-heading "\n")))))

     (org-map-entries (lambda () (let (this-heading this-prio this-level 
this-todo)
                                   (setq this-heading (org-get-heading))
                                   (setq this-prio (org-get-priority 
this-heading))
                                   (setq this-level (org-current-level))
                                   (setq this-todo (org-get-todo-state))
                                   (if (> this-level 1) (if (and
                                                             (> 
this-prio level-other-highest-prio)
                                                             (member 
(org-get-todo-state) '("NEXT" "WAIT")))
                                                            (setq 
level-other-highest-prio this-prio))
                                     (funcall insert-helper)
                                     (setq level-1-heading this-heading)
                                     (setq level-1-state 
(org-get-todo-state))
                                     (setq level-1-marker 
(org-agenda-new-marker (point)))
                                     (setq level-1-prio this-prio)
                                     (setq level-other-highest-prio 0))
                                   )) nil 'agenda nil)
     (funcall insert-helper)
     (select-window (display-buffer result-buffer))
     (fit-buffer-to-window)
     (org-agenda-mode)
     ))


org-unbacked-priorities.el

(defun org-unbacked-priorities ()
   "Find toplevel entries, that do not have at least one child in state 
NEXT and of priority equal or higher"
   (interactive)
   (let ((level-1-prio 0)
         (level-other-highest-prio 0)
         level-1-heading
         level-1-state
         level-1-marker
         insert-helper
         result-buffer)

     (setq result-buffer (get-buffer-create "*Unbacked priorities*"))
     (save-excursion (set-buffer result-buffer)
                     (erase-buffer)
                     (insert "These TODO-entries have a higher priority 
than any of its subentries\nin state NEXT (or they have no such 
subentry).\n\n")
                     )

     (setq insert-helper (lambda ()
                           (when (and
                                  (string= level-1-state "TODO")
                                  (< level-other-highest-prio level-1-prio))
                             (org-add-props level-1-heading nil 
'org-marker level-1-marker)
                             (save-excursion
                               (set-buffer result-buffer)
                               (end-of-buffer)
                               (insert level-1-heading "\n")))))

     (org-map-entries (lambda () (let (this-heading this-prio this-level 
this-todo)
                                   (setq this-heading (org-get-heading))
                                   (setq this-prio (org-get-priority 
this-heading))
                                   (setq this-level (org-current-level))
                                   (setq this-todo (org-get-todo-state))
                                   (if (> this-level 1) (if (and
                                                             (> 
this-prio level-other-highest-prio)
                                                             (member 
(org-get-todo-state) '("NEXT" "WAIT")))
                                                            (setq 
level-other-highest-prio this-prio))
                                     (funcall insert-helper)
                                     (setq level-1-heading this-heading)
                                     (setq level-1-state 
(org-get-todo-state))
                                     (setq level-1-marker 
(org-agenda-new-marker (point)))
                                     (setq level-1-prio this-prio)
                                     (setq level-other-highest-prio 0))
                                   )) nil 'agenda nil)
     (funcall insert-helper)
     (select-window (display-buffer result-buffer))
     (fit-buffer-to-window)
     (org-agenda-mode)
     ))

^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2011-02-27  7:11 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-02-27  7:11 [CODE] Stuck projects and unbacked priorities Marc-Oliver Ihm

Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs/org-mode.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).