diff options
Diffstat (limited to 'lisp')
| -rw-r--r-- | lisp/ChangeLog | 30 | ||||
| -rw-r--r-- | lisp/calendar/todos.el | 395 |
2 files changed, 273 insertions, 152 deletions
diff --git a/lisp/ChangeLog b/lisp/ChangeLog index c529800e564..43587c6bc46 100644 --- a/lisp/ChangeLog +++ b/lisp/ChangeLog | |||
| @@ -1,3 +1,33 @@ | |||
| 1 | 2013-01-14 Stephen Berman <stephen.berman@gmx.net> | ||
| 2 | |||
| 3 | * calendar/todos.el: Implement saving top priority items buffers, | ||
| 4 | improve implementation of item filtering commands and | ||
| 5 | infrastucture, and fix two bugs. | ||
| 6 | (todos-prefix-overlays): Use todos-top-priority face only in Todos | ||
| 7 | mode. | ||
| 8 | (todos-multiple-filter-files): Get file-truename of Todos file. | ||
| 9 | (todos-filter-items): Pass a list of files from the caller instead | ||
| 10 | of building it here, and move handling of cancelled file selection | ||
| 11 | dialog to callers. Correct omission of file-wide default number | ||
| 12 | of top priorities. | ||
| 13 | (todos-filtered-buffer-name): Treat file-list argument only as a list. | ||
| 14 | (todos-find-item, todos-check-top-priorities) | ||
| 15 | (todos-top-priorities-filename) | ||
| 16 | (todos-save-top-priorities-buffer): New functions. | ||
| 17 | (todos-save): Use todos-save-top-priorities-buffer. | ||
| 18 | (todos-jump-to-item): Refactor and use todos-find-item. | ||
| 19 | (todos-top-priorities): Simplify semantics of prefix argument. | ||
| 20 | Check if top priorities file exists and if so, visit it, reporting | ||
| 21 | whether it is up to date. Add optional argument and use it to | ||
| 22 | handle multiple files. | ||
| 23 | (todos-diary-items, todos-regexp-items): Add optional argument and | ||
| 24 | use it to handle multiple files. | ||
| 25 | (todos-top-priorities-multifile, todos-diary-items-multifile) | ||
| 26 | (todos-regexp-items-multifile): Refactor, using corresponding | ||
| 27 | non-multifile command. | ||
| 28 | (auto-mode-alist): Add pattern for top priorities files to visit | ||
| 29 | these in Todos Filtered Items mode. | ||
| 30 | |||
| 1 | 2013-01-08 Stephen Berman <stephen.berman@gmx.net> | 31 | 2013-01-08 Stephen Berman <stephen.berman@gmx.net> |
| 2 | 32 | ||
| 3 | * calendar/todos.el: Fix tabular alignment in Todos Categories mode. | 33 | * calendar/todos.el: Fix tabular alignment in Todos Categories mode. |
diff --git a/lisp/calendar/todos.el b/lisp/calendar/todos.el index c5792338930..157fcbbdc18 100644 --- a/lisp/calendar/todos.el +++ b/lisp/calendar/todos.el | |||
| @@ -40,6 +40,7 @@ | |||
| 40 | :version "24.2" | 40 | :version "24.2" |
| 41 | :group 'calendar) | 41 | :group 'calendar) |
| 42 | 42 | ||
| 43 | ;; FIXME: use file-truename (but in a defcustom) ? | ||
| 43 | (defcustom todos-files-directory (locate-user-emacs-file "todos/") | 44 | (defcustom todos-files-directory (locate-user-emacs-file "todos/") |
| 44 | "Directory where user's Todos files are saved." | 45 | "Directory where user's Todos files are saved." |
| 45 | :type 'directory | 46 | :type 'directory |
| @@ -520,6 +521,11 @@ items in that category, which overrides NUM." | |||
| 520 | :type 'integer | 521 | :type 'integer |
| 521 | :group 'todos-filtered) | 522 | :group 'todos-filtered) |
| 522 | 523 | ||
| 524 | ;; (defcustom todos-save-top-priorities nil ;FIXME: use or delete this | ||
| 525 | ;; "Non-nil to" | ||
| 526 | ;; :type 'boolean | ||
| 527 | ;; :group 'todos-filtered) | ||
| 528 | |||
| 523 | (defcustom todos-filter-files nil | 529 | (defcustom todos-filter-files nil |
| 524 | "List of default files for multifile item filtering." | 530 | "List of default files for multifile item filtering." |
| 525 | :type `(set ,@(mapcar (lambda (f) (list 'const f)) | 531 | :type `(set ,@(mapcar (lambda (f) (list 'const f)) |
| @@ -1568,8 +1574,11 @@ of each other." | |||
| 1568 | done t)) | 1574 | done t)) |
| 1569 | (setq prefix (propertize (concat (number-to-string num) " ") | 1575 | (setq prefix (propertize (concat (number-to-string num) " ") |
| 1570 | 'face | 1576 | 'face |
| 1571 | (if (and (not done) (<= num cat-tp)) | 1577 | ;; Numbers of top priorities have |
| 1572 | 'todos-top-priority ; make defface | 1578 | ;; a distinct face in Todos mode. |
| 1579 | (if (and (not done) (<= num cat-tp) | ||
| 1580 | (eq major-mode 'todos-mode)) | ||
| 1581 | 'todos-top-priority | ||
| 1573 | 'todos-prefix-string)))) | 1582 | 'todos-prefix-string)))) |
| 1574 | (let ((ovs (overlays-in (point) (point))) | 1583 | (let ((ovs (overlays-in (point) (point))) |
| 1575 | marked ov-pref) | 1584 | marked ov-pref) |
| @@ -1894,8 +1903,9 @@ the empty string (i.e., no time string)." | |||
| 1894 | :notify (lambda (&rest ignore) | 1903 | :notify (lambda (&rest ignore) |
| 1895 | (setq todos-multiple-filter-files | 1904 | (setq todos-multiple-filter-files |
| 1896 | (mapcar (lambda (f) | 1905 | (mapcar (lambda (f) |
| 1897 | (concat todos-files-directory | 1906 | (file-truename |
| 1898 | f ".todo")) | 1907 | (concat todos-files-directory |
| 1908 | f ".todo"))) | ||
| 1899 | (widget-value | 1909 | (widget-value |
| 1900 | todos-multiple-filter-files-widget))) | 1910 | todos-multiple-filter-files-widget))) |
| 1901 | (quit-window t) | 1911 | (quit-window t) |
| @@ -1906,31 +1916,20 @@ the empty string (i.e., no time string)." | |||
| 1906 | (message "Click \"Apply\" after selecting files.") | 1916 | (message "Click \"Apply\" after selecting files.") |
| 1907 | (recursive-edit)) | 1917 | (recursive-edit)) |
| 1908 | 1918 | ||
| 1909 | (defun todos-filter-items (filter &optional multifile) | 1919 | (defun todos-filter-items (filter file-list) |
| 1910 | "Build and display a list of items from different categories. | 1920 | "Display a list of items from FILE-LIST that satisfy FILTER. |
| 1911 | 1921 | The values of FILE-LIST and FILTER are passed from the calling | |
| 1912 | The items are selected according to the value of FILTER, which | 1922 | commands. The files in FILE-LIST are either the current Todos |
| 1913 | can be `top' for top priority items, `diary' for diary items, | 1923 | file or those listed in `todos-filter-files' or chosen |
| 1914 | `regexp' for items matching a regular expresion entered by the | 1924 | interactively. The values of FILTER can be `top' for top |
| 1915 | user, or a cons cell of one of these symbols and a number set by | 1925 | priority items, a cons of `top' and a number passed by the |
| 1916 | the calling command, which overrides `todos-show-priorities'. | 1926 | caller, `diary' for diary items, or `regexp' for items matching a |
| 1917 | 1927 | regular expresion entered by the user." | |
| 1918 | With non-nil argument MULTIFILE list top priorities of multiple | ||
| 1919 | Todos files, by default those in `todos-filter-files'." | ||
| 1920 | (let ((num (if (consp filter) (cdr filter) todos-show-priorities)) | 1928 | (let ((num (if (consp filter) (cdr filter) todos-show-priorities)) |
| 1921 | (buf (get-buffer-create todos-filtered-items-buffer)) | 1929 | (buf (get-buffer-create todos-filtered-items-buffer)) |
| 1922 | (files (list todos-current-todos-file)) | 1930 | (multifile (> (length file-list) 1)) |
| 1923 | regexp fname bufstr cat beg end done) | 1931 | regexp fname bufstr cat beg end done) |
| 1924 | (when multifile | 1932 | (if (null file-list) |
| 1925 | (setq files (or todos-multiple-filter-files ; Passed from todos-*-multifile. | ||
| 1926 | (if (or (consp filter) | ||
| 1927 | (null todos-filter-files)) | ||
| 1928 | (progn (todos-multiple-filter-files) | ||
| 1929 | todos-multiple-filter-files) | ||
| 1930 | todos-filter-files)) | ||
| 1931 | todos-multiple-filter-files nil)) | ||
| 1932 | (if (eq files 'quit) (keyboard-quit)) | ||
| 1933 | (if (null files) | ||
| 1934 | (error "No files have been chosen for filtering") | 1933 | (error "No files have been chosen for filtering") |
| 1935 | (with-current-buffer buf | 1934 | (with-current-buffer buf |
| 1936 | (erase-buffer) | 1935 | (erase-buffer) |
| @@ -1939,7 +1938,7 @@ Todos files, by default those in `todos-filter-files'." | |||
| 1939 | (when (eq filter 'regexp) | 1938 | (when (eq filter 'regexp) |
| 1940 | (setq regexp (read-string "Enter a regular expression: "))) | 1939 | (setq regexp (read-string "Enter a regular expression: "))) |
| 1941 | (save-current-buffer | 1940 | (save-current-buffer |
| 1942 | (dolist (f files) | 1941 | (dolist (f file-list) |
| 1943 | ;; Before inserting file contents into temp buffer, save a modified | 1942 | ;; Before inserting file contents into temp buffer, save a modified |
| 1944 | ;; buffer visiting it. | 1943 | ;; buffer visiting it. |
| 1945 | (let ((bf (find-buffer-visiting f))) | 1944 | (let ((bf (find-buffer-visiting f))) |
| @@ -1976,21 +1975,23 @@ Todos files, by default those in `todos-filter-files'." | |||
| 1976 | ;; Delete Todos file categories sexp. | 1975 | ;; Delete Todos file categories sexp. |
| 1977 | (delete-region (line-beginning-position) (1+ (line-end-position))) | 1976 | (delete-region (line-beginning-position) (1+ (line-end-position))) |
| 1978 | (let (fnum) | 1977 | (let (fnum) |
| 1979 | ;; Unless the number of items to show was supplied by prefix | 1978 | ;; Unless the number of top priorities to show was |
| 1980 | ;; argument of caller, the file-wide value from | 1979 | ;; passed by the caller, the file-wide value from |
| 1981 | ;; `todos-priorities-rules', if non-nil, overrides | 1980 | ;; `todos-priorities-rules', if non-nil, overrides |
| 1982 | ;; `todos-show-priorities'. | 1981 | ;; `todos-show-priorities'. |
| 1983 | (unless (consp filter) | 1982 | (unless (consp filter) |
| 1984 | (setq fnum (nth 1 (assoc f todos-priorities-rules)))) | 1983 | (setq fnum (or (nth 1 (assoc f todos-priorities-rules)) |
| 1984 | todos-show-priorities))) | ||
| 1985 | (while (re-search-forward | 1985 | (while (re-search-forward |
| 1986 | (concat "^" (regexp-quote todos-category-beg) "\\(.+\\)\n") | 1986 | (concat "^" (regexp-quote todos-category-beg) "\\(.+\\)\n") |
| 1987 | nil t) | 1987 | nil t) |
| 1988 | (setq cat (match-string 1)) | 1988 | (setq cat (match-string 1)) |
| 1989 | (let (cnum) | 1989 | (let (cnum) |
| 1990 | ;; Unless the number of items to show was supplied by prefix | 1990 | ;; Unless the number of top priorities to show was |
| 1991 | ;; argument of caller, the category-wide value from | 1991 | ;; passed by the caller, the category-wide value |
| 1992 | ;; `todos-priorities-rules', if non-nil, overrides a non-nil | 1992 | ;; from `todos-priorities-rules', if non-nil, |
| 1993 | ;; file-wide value from `todos-priorities-rules' as well as | 1993 | ;; overrides a non-nil file-wide value from |
| 1994 | ;; `todos-priorities-rules' as well as | ||
| 1994 | ;; `todos-show-priorities'. | 1995 | ;; `todos-show-priorities'. |
| 1995 | (unless (consp filter) | 1996 | (unless (consp filter) |
| 1996 | (let ((cats (nth 2 (assoc f todos-priorities-rules)))) | 1997 | (let ((cats (nth 2 (assoc f todos-priorities-rules)))) |
| @@ -2125,13 +2126,69 @@ The new name is constructed from the string BUFFER-TYPE, which | |||
| 2125 | refers to one of the top priorities, diary or regexp item | 2126 | refers to one of the top priorities, diary or regexp item |
| 2126 | filters, and the names of the filtered files in FILE-LIST. Used | 2127 | filters, and the names of the filtered files in FILE-LIST. Used |
| 2127 | in Todos Filter Items mode." | 2128 | in Todos Filter Items mode." |
| 2128 | (let* ((flist (if (listp file-list) file-list (list file-list))) | 2129 | (let* ((multi (> (length file-list) 1)) |
| 2129 | (multi (> (length flist) 1)) | ||
| 2130 | (fnames (mapconcat (lambda (f) (todos-short-file-name f)) | 2130 | (fnames (mapconcat (lambda (f) (todos-short-file-name f)) |
| 2131 | flist ", "))) | 2131 | file-list ", "))) |
| 2132 | (rename-buffer (format (concat "%s for file" (if multi "s" "") | 2132 | (rename-buffer (format (concat "%s for file" (if multi "s" "") |
| 2133 | " \"%s\"") buffer-type fnames)))) | 2133 | " \"%s\"") buffer-type fnames)))) |
| 2134 | 2134 | ||
| 2135 | (defun todos-find-item (str) | ||
| 2136 | "" | ||
| 2137 | (string-match (concat (if todos-filter-done-items | ||
| 2138 | (concat "\\(?:" todos-done-string-start "\\|" | ||
| 2139 | todos-date-string-start "\\)") | ||
| 2140 | todos-date-string-start) | ||
| 2141 | todos-date-pattern "\\(?: " diary-time-regexp "\\)?" | ||
| 2142 | (if todos-filter-done-items | ||
| 2143 | "\\]" | ||
| 2144 | (regexp-quote todos-nondiary-end)) "?" | ||
| 2145 | "\\(?4: \\[\\(?3:(archive) \\)?\\(?2:.*:\\)?" | ||
| 2146 | "\\(?1:.*\\)\\]\\).*$") str) | ||
| 2147 | (let ((cat (match-string 1 str)) | ||
| 2148 | (file (match-string 2 str)) | ||
| 2149 | (archive (string= (match-string 3 str) "(archive) ")) | ||
| 2150 | found) | ||
| 2151 | (setq str (replace-match "" nil nil str 4)) | ||
| 2152 | (setq file (if file | ||
| 2153 | (concat todos-files-directory (substring file 0 -1) | ||
| 2154 | (if archive ".toda" ".todo")) | ||
| 2155 | (if archive | ||
| 2156 | (concat (file-name-sans-extension | ||
| 2157 | todos-global-current-todos-file) ".toda") | ||
| 2158 | todos-global-current-todos-file))) | ||
| 2159 | (find-file-noselect file) | ||
| 2160 | (with-current-buffer (find-buffer-visiting file) | ||
| 2161 | (widen) | ||
| 2162 | (goto-char (point-min)) | ||
| 2163 | (re-search-forward | ||
| 2164 | (concat "^" (regexp-quote (concat todos-category-beg cat)) "$") nil t) | ||
| 2165 | (setq found (search-forward str nil t))) | ||
| 2166 | (list found file cat))) | ||
| 2167 | |||
| 2168 | (defun todos-check-top-priorities () | ||
| 2169 | "Return a message saying whether top priorities file is up-to-date." | ||
| 2170 | (while (not (eobp)) | ||
| 2171 | (let ((item (todos-item-string))) | ||
| 2172 | (unless (car (todos-find-item item)) | ||
| 2173 | (error "Top priorities file is not up to date"))) | ||
| 2174 | (todos-forward-item)) | ||
| 2175 | (message "Top priorities file is up to date.")) | ||
| 2176 | |||
| 2177 | (defun todos-top-priorities-filename () ;FIXME: make part of t-s-t-p-b ? | ||
| 2178 | "" | ||
| 2179 | (let ((bufname (buffer-name))) | ||
| 2180 | (string-match "\"\\([^\"]+\\)\"" bufname) | ||
| 2181 | (let* ((filename-str (substring bufname (match-beginning 1) (match-end 1))) | ||
| 2182 | (filename-base (replace-regexp-in-string ", " "-" filename-str))) | ||
| 2183 | (concat todos-files-directory filename-base ".todt")))) | ||
| 2184 | |||
| 2185 | (defun todos-save-top-priorities-buffer () | ||
| 2186 | "" | ||
| 2187 | (let ((filename (todos-top-priorities-filename))) | ||
| 2188 | (if (file-exists-p filename) | ||
| 2189 | (save-buffer) | ||
| 2190 | (write-region nil nil filename nil t nil t)))) | ||
| 2191 | |||
| 2135 | ;; --------------------------------------------------------------------------- | 2192 | ;; --------------------------------------------------------------------------- |
| 2136 | ;;; Sorting and display routines for Todos Categories mode. | 2193 | ;;; Sorting and display routines for Todos Categories mode. |
| 2137 | 2194 | ||
| @@ -3075,11 +3132,14 @@ displayed." | |||
| 3075 | (interactive) | 3132 | (interactive) |
| 3076 | (todos-show-archive t)) | 3133 | (todos-show-archive t)) |
| 3077 | 3134 | ||
| 3078 | ;; FIXME: need this? | ||
| 3079 | (defun todos-save () | 3135 | (defun todos-save () |
| 3080 | "Save the current Todos file." | 3136 | "Save the current Todos file." |
| 3081 | (interactive) | 3137 | (interactive) |
| 3082 | (save-buffer)) | 3138 | (cond ((eq major-mode 'todos-filtered-items-mode) |
| 3139 | (todos-check-top-priorities) | ||
| 3140 | (todos-save-top-priorities-buffer)) | ||
| 3141 | (t | ||
| 3142 | (save-buffer)))) | ||
| 3083 | 3143 | ||
| 3084 | (defun todos-quit () | 3144 | (defun todos-quit () |
| 3085 | "Exit the current Todos-related buffer. | 3145 | "Exit the current Todos-related buffer. |
| @@ -3380,46 +3440,25 @@ CAT; this is used in Todos Categories mode." | |||
| 3380 | (defun todos-jump-to-item () | 3440 | (defun todos-jump-to-item () |
| 3381 | "Jump to the file and category of the filtered item at point." | 3441 | "Jump to the file and category of the filtered item at point." |
| 3382 | (interactive) | 3442 | (interactive) |
| 3383 | (let ((str (todos-item-string)) | 3443 | (let* ((str (todos-item-string)) |
| 3384 | (buf (current-buffer)) | 3444 | (buf (current-buffer)) |
| 3385 | cat file archive beg) | 3445 | (res (todos-find-item str)) |
| 3386 | (string-match (concat (if todos-filter-done-items | 3446 | (file (nth 1 res)) |
| 3387 | (concat "\\(?:" todos-done-string-start "\\|" | 3447 | (cat (nth 2 res)) |
| 3388 | todos-date-string-start "\\)") | 3448 | beg) |
| 3389 | todos-date-string-start) | 3449 | (if (not (car res)) |
| 3390 | todos-date-pattern "\\(?: " diary-time-regexp "\\)?" | 3450 | (message "Item not found") |
| 3391 | (if todos-filter-done-items | 3451 | (setq beg (match-beginning 0)) |
| 3392 | "\\]" | 3452 | (kill-buffer buf) |
| 3393 | (regexp-quote todos-nondiary-end)) "?" | 3453 | (set-window-buffer (selected-window) |
| 3394 | "\\(?4: \\[\\(?3:(archive) \\)?\\(?2:.*:\\)?" | 3454 | (set-buffer (find-buffer-visiting file))) |
| 3395 | "\\(?1:.*\\)\\]\\).*$") str) | 3455 | (setq todos-current-todos-file file) |
| 3396 | (setq cat (match-string 1 str)) | 3456 | (setq todos-category-number (todos-category-number cat)) |
| 3397 | (setq file (match-string 2 str)) | 3457 | (let ((todos-show-with-done (if todos-filter-done-items |
| 3398 | (setq archive (string= (match-string 3 str) "(archive) ")) | 3458 | t |
| 3399 | (setq str (replace-match "" nil nil str 4)) | 3459 | todos-show-with-done))) |
| 3400 | (setq file (if file | 3460 | (todos-category-select)) |
| 3401 | (concat todos-files-directory (substring file 0 -1) | 3461 | (goto-char beg)))) |
| 3402 | (if archive ".toda" ".todo")) | ||
| 3403 | (if archive | ||
| 3404 | (concat (file-name-sans-extension | ||
| 3405 | todos-global-current-todos-file) ".toda") | ||
| 3406 | todos-global-current-todos-file))) | ||
| 3407 | (find-file-noselect file) | ||
| 3408 | (with-current-buffer (find-buffer-visiting file) | ||
| 3409 | (widen) | ||
| 3410 | (goto-char (point-min)) | ||
| 3411 | (re-search-forward | ||
| 3412 | (concat "^" (regexp-quote (concat todos-category-beg cat)) "$") nil t) | ||
| 3413 | (search-forward str) | ||
| 3414 | (setq beg (match-beginning 0))) | ||
| 3415 | (kill-buffer buf) | ||
| 3416 | (set-window-buffer (selected-window) (set-buffer (find-buffer-visiting file))) | ||
| 3417 | (setq todos-current-todos-file file) | ||
| 3418 | (setq todos-category-number (todos-category-number cat)) | ||
| 3419 | (let ((todos-show-with-done (if todos-filter-done-items t | ||
| 3420 | todos-show-with-done))) | ||
| 3421 | (todos-category-select)) | ||
| 3422 | (goto-char beg))) | ||
| 3423 | 3462 | ||
| 3424 | (defun todos-forward-item (&optional count) | 3463 | (defun todos-forward-item (&optional count) |
| 3425 | "Move point down to start of item with next lower priority. | 3464 | "Move point down to start of item with next lower priority. |
| @@ -3695,85 +3734,136 @@ See `todos-set-top-priorities' for more details." | |||
| 3695 | (interactive) | 3734 | (interactive) |
| 3696 | (todos-set-top-priorities t)) | 3735 | (todos-set-top-priorities t)) |
| 3697 | 3736 | ||
| 3698 | (defun todos-top-priorities (&optional num) | 3737 | (defun todos-top-priorities (&optional arg multifile) |
| 3699 | "List top priorities of each category in `todos-filter-files'. | 3738 | "Display a list of top priority items from different categories. |
| 3700 | Number of entries for each category is given by NUM, which | 3739 | The categories are either a subset of those in the current Todos |
| 3701 | defaults to `todos-show-priorities'." | 3740 | file, or else, with non-nil argument MULTIFILE, a subset of the |
| 3741 | categories in the files listed in `todos-filter-files', or if | ||
| 3742 | this nil, in the files chosen from a file selection dialog that | ||
| 3743 | pops up in this case. | ||
| 3744 | |||
| 3745 | With numerical prefix ARG show at most ARG top priority items | ||
| 3746 | from each category. With `C-u' as prefix argument show the | ||
| 3747 | numbers of top priority items specified by category in | ||
| 3748 | `todos-priorities-rules', if this has an entry for the file(s); | ||
| 3749 | otherwise show `todos-show-priorities' items per category in the | ||
| 3750 | file(s). With no prefix argument, if a top priorities file for | ||
| 3751 | the current Todos file has previously been saved (see | ||
| 3752 | `todos-save-top-priorities-buffer'), visit this file; if there is | ||
| 3753 | no such file, build the list as with prefix argument `C-u'. | ||
| 3754 | |||
| 3755 | The prefix ARG regulates how many top priorities from | ||
| 3756 | each category to show, as described above." | ||
| 3702 | (interactive "P") | 3757 | (interactive "P") |
| 3703 | (let ((arg (if num (cons 'top num) 'top)) | 3758 | (let* ((flist (if multifile |
| 3704 | (buf todos-top-priorities-buffer) | 3759 | (or todos-filter-files |
| 3705 | (file todos-current-todos-file)) | 3760 | (progn (todos-multiple-filter-files) |
| 3706 | (todos-filter-items arg) | 3761 | todos-multiple-filter-files)) |
| 3707 | (todos-filtered-buffer-name buf file))) | 3762 | (list todos-current-todos-file))) |
| 3763 | (tp-file (if (equal flist 'quit) | ||
| 3764 | ;; Pressed `cancel' in file selection dialog. | ||
| 3765 | (keyboard-quit) | ||
| 3766 | (concat todos-files-directory | ||
| 3767 | (mapconcat 'identity | ||
| 3768 | (mapcar 'todos-short-file-name flist) | ||
| 3769 | "-") | ||
| 3770 | ".todt"))) | ||
| 3771 | (tp-file-exists (file-exists-p tp-file)) | ||
| 3772 | (buf todos-top-priorities-buffer)) | ||
| 3773 | (cond ((and arg (natnump arg)) | ||
| 3774 | (todos-filter-items (cons 'top arg) flist)) | ||
| 3775 | ((and (not arg) tp-file-exists) | ||
| 3776 | (find-file tp-file) | ||
| 3777 | (todos-prefix-overlays) | ||
| 3778 | (todos-check-top-priorities)) | ||
| 3779 | (t | ||
| 3780 | (todos-filter-items 'top flist))) | ||
| 3781 | (unless tp-file-exists | ||
| 3782 | (todos-filtered-buffer-name buf flist)))) | ||
| 3708 | 3783 | ||
| 3709 | (defun todos-top-priorities-multifile (&optional arg) | 3784 | (defun todos-top-priorities-multifile (&optional arg) |
| 3710 | "List top priorities of each category in `todos-filter-files'. | 3785 | "Display a list of top priority items from different categories. |
| 3711 | 3786 | The categories are a subset of the categories in the files listed | |
| 3712 | If the prefix argument ARG is a number, this is the maximum | 3787 | in `todos-filter-files', or if this nil, in the files chosen from |
| 3713 | number of top priorities to list in each category. If the prefix | 3788 | a file selection dialog that pops up in this case. |
| 3714 | argument is `C-u', prompt for which files to filter and use | 3789 | |
| 3715 | `todos-show-priorities' as the number of top priorities to list | 3790 | With numerical prefix ARG show at most ARG top priority items |
| 3716 | in each category. If the prefix argument is `C-uC-u', prompt | 3791 | from each category in each file. With `C-u' as prefix argument |
| 3717 | both for which files to filter and for how many top priorities to | 3792 | show the numbers of top priority items specified in |
| 3718 | list in each category." | 3793 | `todos-priorities-rules', if this is non-nil; otherwise show |
| 3794 | `todos-show-priorities' items per category. With no prefix | ||
| 3795 | argument, if a top priorities file for the chosen Todos files | ||
| 3796 | exists (see `todos-save-top-priorities-buffer'), visit this file; | ||
| 3797 | if there is no such file, do the same as with prefix argument | ||
| 3798 | `C-u'." | ||
| 3719 | (interactive "P") | 3799 | (interactive "P") |
| 3720 | (let* ((buf todos-top-priorities-buffer) | 3800 | (todos-top-priorities arg t)) |
| 3721 | files | 3801 | |
| 3722 | (pref (if (numberp arg) | 3802 | (defun todos-diary-items (&optional multifile) |
| 3723 | (cons 'top arg) | 3803 | "Display a list of todo diary items from different categories. |
| 3724 | (setq files (if (or (consp arg) | 3804 | The categories are either a subset of those in the current Todos |
| 3725 | (null todos-filter-files)) | 3805 | file, or else, with non-nil argument MULTIFILE, a subset of the |
| 3726 | (progn (todos-multiple-filter-files) | 3806 | categories in the files listed in `todos-filter-files', or if |
| 3727 | todos-multiple-filter-files) | 3807 | this nil, in the files chosen from a file selection dialog that |
| 3728 | todos-filter-files)) | 3808 | pops up in this case." |
| 3729 | (if (equal arg '(16)) | ||
| 3730 | (cons 'top (read-number | ||
| 3731 | "Enter number of top priorities to show: " | ||
| 3732 | todos-show-priorities)) | ||
| 3733 | 'top)))) | ||
| 3734 | (todos-filter-items pref t) | ||
| 3735 | (todos-filtered-buffer-name buf files))) | ||
| 3736 | |||
| 3737 | (defun todos-diary-items () | ||
| 3738 | "Display todo items for diary inclusion in this Todos file." | ||
| 3739 | (interactive) | 3809 | (interactive) |
| 3740 | (let ((buf todos-diary-items-buffer) | 3810 | (let ((flist (if multifile |
| 3741 | (file todos-current-todos-file)) | 3811 | (or todos-filter-files |
| 3742 | (todos-filter-items 'diary) | 3812 | (progn (todos-multiple-filter-files) |
| 3743 | (todos-filtered-buffer-name buf file))) | 3813 | todos-multiple-filter-files)) |
| 3744 | 3814 | (list todos-current-todos-file))) | |
| 3745 | (defun todos-diary-items-multifile (&optional arg) | 3815 | (buf todos-diary-items-buffer)) |
| 3746 | "Display todo items for diary inclusion in one or more Todos file. | 3816 | (if (equal flist 'quit) |
| 3747 | The files are those listed in `todos-filter-files'." | 3817 | ;; Pressed `cancel' in file selection dialog. |
| 3748 | (interactive "P") | 3818 | (keyboard-quit) |
| 3749 | (let ((buf todos-diary-items-buffer) | 3819 | (todos-filter-items 'diary flist) |
| 3750 | (files (if (or arg (null todos-filter-files)) | 3820 | (todos-filtered-buffer-name buf flist)))) |
| 3751 | (progn (todos-multiple-filter-files) | 3821 | |
| 3752 | todos-multiple-filter-files) | 3822 | (defun todos-diary-items-multifile () |
| 3753 | todos-filter-files))) | 3823 | "Display a list of todo diary items from one or more Todos files. |
| 3754 | (todos-filter-items 'diary t) | 3824 | The categories are a subset of the categories in the files listed |
| 3755 | (todos-filtered-buffer-name buf files))) | 3825 | in `todos-filter-files', or if this nil, in the files chosen from |
| 3756 | 3826 | a file selection dialog that pops up in this case." | |
| 3757 | (defun todos-regexp-items () | ||
| 3758 | "Display todo items matching a user-entered regular expression. | ||
| 3759 | The items are those in the current Todos file." | ||
| 3760 | (interactive) | 3827 | (interactive) |
| 3761 | (let ((buf todos-regexp-items-buffer) | 3828 | (todos-diary-items t)) |
| 3762 | (file todos-current-todos-file)) | 3829 | |
| 3763 | (todos-filter-items 'regexp) | 3830 | (defun todos-regexp-items (&optional multifile) |
| 3764 | (todos-filtered-buffer-name buf file))) | 3831 | "Prompt for a regular expression and display items that match it. |
| 3765 | 3832 | The matches may be from different categories and with non-nil | |
| 3766 | (defun todos-regexp-items-multifile (&optional arg) | 3833 | option `todos-filter-done-items', can include not only todo items |
| 3767 | "Display todo items matching a user-entered regular expression. | 3834 | but also done items, including those in Archive files. |
| 3768 | The items are those in the files listed in `todos-filter-files'." | 3835 | |
| 3769 | (interactive "P") | 3836 | The categories are either a subset of those in the current Todos |
| 3770 | (let ((buf todos-regexp-items-buffer) | 3837 | file (and possibly in the corresponding Archive file), or else, |
| 3771 | (files (if (or arg (null todos-filter-files)) | 3838 | with non-nil argument MULTIFILE, a subset of the categories in |
| 3772 | (progn (todos-multiple-filter-files) | 3839 | the files listed in `todos-filter-files', or if this nil, in the |
| 3773 | todos-multiple-filter-files) | 3840 | files chosen from a file selection dialog that pops up in this |
| 3774 | todos-filter-files))) | 3841 | case (and possibly in the corresponding Archive files)." |
| 3775 | (todos-filter-items 'regexp t) | 3842 | (interactive) |
| 3776 | (todos-filtered-buffer-name buf files))) | 3843 | (let ((flist (if multifile |
| 3844 | (or todos-filter-files | ||
| 3845 | (progn (todos-multiple-filter-files) | ||
| 3846 | todos-multiple-filter-files)) | ||
| 3847 | (list todos-current-todos-file))) | ||
| 3848 | (buf todos-regexp-items-buffer)) | ||
| 3849 | (if (equal flist 'quit) | ||
| 3850 | ;; Pressed `cancel' in file selection dialog. | ||
| 3851 | (keyboard-quit) | ||
| 3852 | (todos-filter-items 'regexp flist) | ||
| 3853 | (todos-filtered-buffer-name buf flist)))) | ||
| 3854 | |||
| 3855 | (defun todos-regexp-items-multifile () | ||
| 3856 | "Prompt for a regular expression and display items that match it. | ||
| 3857 | The matches may be from different categories and with non-nil | ||
| 3858 | option `todos-filter-done-items', can include not only todo items | ||
| 3859 | but also done items, including those in Archive files. | ||
| 3860 | |||
| 3861 | The categories are a subset of the categories in the files listed | ||
| 3862 | in `todos-filter-files', or if this nil, in the files chosen from | ||
| 3863 | a file selection dialog that pops up in this case (and possibly | ||
| 3864 | in the corresponding Archive files)." | ||
| 3865 | (interactive) | ||
| 3866 | (todos-regexp-items t)) | ||
| 3777 | 3867 | ||
| 3778 | ;; --------------------------------------------------------------------------- | 3868 | ;; --------------------------------------------------------------------------- |
| 3779 | ;;; Editing Commands | 3869 | ;;; Editing Commands |
| @@ -5729,6 +5819,7 @@ archive, the archive file is deleted." | |||
| 5729 | ;; --------------------------------------------------------------------------- | 5819 | ;; --------------------------------------------------------------------------- |
| 5730 | (add-to-list 'auto-mode-alist '("\\.todo\\'" . todos-mode)) | 5820 | (add-to-list 'auto-mode-alist '("\\.todo\\'" . todos-mode)) |
| 5731 | (add-to-list 'auto-mode-alist '("\\.toda\\'" . todos-archive-mode)) | 5821 | (add-to-list 'auto-mode-alist '("\\.toda\\'" . todos-archive-mode)) |
| 5822 | (add-to-list 'auto-mode-alist '("\\.todt\\'" . todos-filtered-items-mode)) | ||
| 5732 | 5823 | ||
| 5733 | ;;; Addition to calendar.el | 5824 | ;;; Addition to calendar.el |
| 5734 | ;; FIXME: autoload when key-binding is defined in calendar.el | 5825 | ;; FIXME: autoload when key-binding is defined in calendar.el |