[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[emacs-wiki-discuss] Tentative hack Re: Assigning tasks to multiple proj
From: |
Sacha Chua |
Subject: |
[emacs-wiki-discuss] Tentative hack Re: Assigning tasks to multiple projects/pages |
Date: |
Tue, 30 Nov 2004 13:02:21 +0900 |
User-agent: |
Gnus/5.110003 (No Gnus v0.3) Emacs/21.3.50 (gnu/linux) |
First shot at a hack for multiple task views. The following code
rewrites everything between
<taskdb s="someregexp">
</taskdb>
with a list of tasks matching the optional regular expression.
The tasks are taken from TaskPool.
Here there be dragons. I suggest testing it outside your normal wiki.
To use, require it, create lots of stuff in your TaskPool, add
<taskdb s="someregexp">
</taskdb>
on some page, and then call M-x planner-db-update-page .
It seems like a promising direction, though. I haven't figured out how
to get it to cooperate with normal plan pages, and would appreciate
insights.
;;; planner-db.el --- multiple task views for planner.el
;; address@hidden, GPL
;; Copyright (C) 2004 Sandra Jean Chua (Sacha) <address@hidden>
;; This file is not part of GNU Emacs.
;; This is free software; you can redistribute it and/or modify it under
;; the terms of the GNU General Public License as published by the Free
;; Software Foundation; either version 2, or (at your option) any later
;; version.
;;
;; This is distributed in the hope that it will be useful, but WITHOUT
;; ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
;; FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
;; for more details.
;;
;; You should have received a copy of the GNU General Public License
;; along with GNU Emacs; see the file COPYING. If not, write to the
;; Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
;; MA 02111-1307, USA.
;;; Commentary:
;;
;; Usage:
;;
;; Add (require 'planner-db) to your ~/.emacs . Then you can use
;;
;; <taskdb s="someregexp">
;; </taskdb>
;;
;; in your planner pages to get a list of all the tasks from a
;; particular page. To regenerate the contents, call
;; `planner-db-update-page'.
;;
;; What works:
;; - updating the list of tasks
;; - marking a task as closed, whatever (changes reflected in main
;; database)
;;
;; Note that this module redefines the behavior of
;; planner-jump-to-linked-task! I currently wouldn't advise it for
;; people who use plan pages, as planner-db.el can't tell the
;; difference between tasks it manages and tasks you manually put on
;; plan pages.
;;
;; Be very, very careful about mismatched tags! This will _DELETE_ any
;; text between the opening and closing tags.
;;
;; Also, I haven't figured out how to neatly do the following:
;; - publishing
;; - updating lots of pages
;; - working nicely with the rest of the code
;; - getting the planner task-related functions to all do the
;; Right Thing.
;; Not bad, though, for a proof-of-concept one-hour hack.
;;; Code:
(defvar planner-db-page "TaskPool"
"Page containing all the current tasks.")
(defvar planner-db-task-tag "taskdb"
"Tag name for tasks from database.")
(defvar planner-db-task-condition-attribute "s"
"Attribute name for `planner-db-task-tag' conditions.")
(defun planner-db-get-tasks (condition)
"Return a list of tasks matching CONDITION.
Tasks are looked up in `planner-db-page'. CONDITION is a
regexp."
(save-window-excursion
(save-excursion
(save-restriction
(planner-find-file planner-db-page)
(widen)
(goto-char (point-min))
(let (results info description condition line)
(while (re-search-forward planner-task-regexp nil t)
(when
(or (not condition)
(string-match
condition
(buffer-substring (line-beginning-position)
(line-end-position))))
(setq results (cons (planner-current-task-info) results))))
results)))))
(defun planner-db-insert-tasks (condition)
"Insert tasks matching CONDITION.
Lines should match CONDITION is a regexp."
(let (tasks)
(setq tasks (planner-db-get-tasks condition))
(while tasks
(insert (planner-format-task (car tasks)) "\n")
(setq tasks (cdr tasks)))))
;; A general function should be moved into emacs-wiki for edit-time
;; markup.
(defun planner-db-update-page ()
"Search forward for all tasks tag and replace the text."
(interactive)
(save-excursion
(save-restriction
(widen)
(goto-char (point-min))
(while (re-search-forward emacs-wiki-tag-regexp nil t)
(let ((tag-name (match-string-no-properties 1))
beg
attrs)
(when (string= tag-name planner-db-task-tag)
(setq beg (match-end 0))
(let ((attrstr (match-string 2)))
(while (and attrstr
(string-match
"\\([^ \t\n=]+\\)\\(=\"\\([^\"]+\\)\"\\)?"
attrstr))
(let ((attr (cons (downcase
(match-string-no-properties 1 attrstr))
(match-string-no-properties 3 attrstr))))
(setq attrstr (replace-match "" t t attrstr))
(if attrs
(nconc attrs (list attr))
(setq attrs (list attr))))))
(when (search-forward (concat "</" tag-name ">") nil t)
(save-restriction
(goto-char beg)
(unless (= (point) (line-beginning-position))
(insert "\n"))
(narrow-to-region (point) (match-beginning 0))
(delete-region (point-min) (point-max))
(planner-db-insert-tasks
(cdr (assoc planner-db-task-condition-attribute attrs)))
(add-text-properties (point-min) (point-max)
'(planner-db t))))))))))
(defun planner-db-jump-to-linked-task (&optional task-info)
"Display the task page linked to by the current task or TASK-INFO."
(interactive)
(let* ((task-info (or task-info (planner-current-task-info))))
(planner-find-file planner-db-page)
(widen)
(goto-char (point-min))
(when (search-forward (planner-task-description task-info) nil t)
(beginning-of-line)
t)))
(defalias 'planner-jump-to-linked-task 'planner-db-jump-to-linked-task)
(provide 'planner-db)
;;; planner-db.el ends here
--
Sacha Chua <address@hidden> - open source geekette
http://sacha.free.net.ph/ - PGP Key ID: 0xE7FDF77C
interests: emacs, gnu/linux, personal information management, CS ed
applying as a Debian new maintainer | looking for a grad school