Mercurial > emacs
comparison lisp/calendar/diary-lib.el @ 92859:15bd5abe194e
Whitespace only.
author | Glenn Morris <rgm@gnu.org> |
---|---|
date | Thu, 13 Mar 2008 06:29:03 +0000 |
parents | de680a2b3b3b |
children | 532b44d84fec |
comparison
equal
deleted
inserted
replaced
92858:7096add7a945 | 92859:15bd5abe194e |
---|---|
52 (defcustom diary-face 'diary | 52 (defcustom diary-face 'diary |
53 "Face name to use for diary entries." | 53 "Face name to use for diary entries." |
54 :type 'face | 54 :type 'face |
55 :group 'diary) | 55 :group 'diary) |
56 (make-obsolete-variable 'diary-face "customize the face `diary' instead." | 56 (make-obsolete-variable 'diary-face "customize the face `diary' instead." |
57 "23.1") | 57 "23.1") |
58 | 58 |
59 ;; Face markup of calendar and diary displays: Any entry line that | 59 ;; Face markup of calendar and diary displays: Any entry line that |
60 ;; ends with [foo:value] where foo is a face attribute (except :box | 60 ;; ends with [foo:value] where foo is a face attribute (except :box |
61 ;; :stipple) or with [face:blah] tags, will have these values applied | 61 ;; :stipple) or with [face:blah] tags, will have these values applied |
62 ;; to the calendar and fancy diary displays. These attributes "stack" | 62 ;; to the calendar and fancy diary displays. These attributes "stack" |
88 specifies which face attribute (e.g. `:foreground') to modify, or | 88 specifies which face attribute (e.g. `:foreground') to modify, or |
89 that this is a face (`:face') to apply. TYPE is the type of | 89 that this is a face (`:face') to apply. TYPE is the type of |
90 attribute being applied. Available TYPES (see `diary-attrtype-convert') | 90 attribute being applied. Available TYPES (see `diary-attrtype-convert') |
91 are: `string', `symbol', `int', `tnil',`stringtnil.'" | 91 are: `string', `symbol', `int', `tnil',`stringtnil.'" |
92 :type '(repeat (list (string :tag "Regular expression") | 92 :type '(repeat (list (string :tag "Regular expression") |
93 (integer :tag "Sub-expression") | 93 (integer :tag "Sub-expression") |
94 (symbol :tag "Attribute (e.g. :foreground)") | 94 (symbol :tag "Attribute (e.g. :foreground)") |
95 (choice (const string :tag "A string") | 95 (choice (const string :tag "A string") |
96 (const symbol :tag "A symbol") | 96 (const symbol :tag "A symbol") |
97 (const int :tag "An integer") | 97 (const int :tag "An integer") |
98 (const tnil :tag "`t' or `nil'") | 98 (const tnil :tag "`t' or `nil'") |
99 (const stringtnil | 99 (const stringtnil |
100 :tag "A string, `t', or `nil'")))) | 100 :tag "A string, `t', or `nil'")))) |
101 :group 'diary) | 101 :group 'diary) |
102 | 102 |
103 (defcustom diary-glob-file-regexp-prefix "^\\#" | 103 (defcustom diary-glob-file-regexp-prefix "^\\#" |
104 "Regular expression prepended to `diary-face-attrs' for file-wide specifiers." | 104 "Regular expression prepended to `diary-face-attrs' for file-wide specifiers." |
105 :type 'regexp | 105 :type 'regexp |
175 `list-hebrew-diary-entries', `list-islamic-diary-entries' and | 175 `list-hebrew-diary-entries', `list-islamic-diary-entries' and |
176 `diary-bahai-list-entries'. The documentation for these functions | 176 `diary-bahai-list-entries'. The documentation for these functions |
177 describes the style of such diary entries." | 177 describes the style of such diary entries." |
178 :type 'hook | 178 :type 'hook |
179 :options '(list-hebrew-diary-entries | 179 :options '(list-hebrew-diary-entries |
180 list-islamic-diary-entries | 180 list-islamic-diary-entries |
181 diary-bahai-list-entries) | 181 diary-bahai-list-entries) |
182 :group 'diary) | 182 :group 'diary) |
183 | 183 |
184 (defcustom nongregorian-diary-marking-hook nil | 184 (defcustom nongregorian-diary-marking-hook nil |
185 "List of functions called for marking diary file and included files. | 185 "List of functions called for marking diary file and included files. |
186 As the files are processed for diary entries, these functions are used | 186 As the files are processed for diary entries, these functions are used |
188 `mark-hebrew-diary-entries', `mark-islamic-diary-entries' and | 188 `mark-hebrew-diary-entries', `mark-islamic-diary-entries' and |
189 `bahai-mark-diary-entries'. The documentation for these functions | 189 `bahai-mark-diary-entries'. The documentation for these functions |
190 describes the style of such diary entries." | 190 describes the style of such diary entries." |
191 :type 'hook | 191 :type 'hook |
192 :options '(mark-hebrew-diary-entries | 192 :options '(mark-hebrew-diary-entries |
193 mark-islamic-diary-entries | 193 mark-islamic-diary-entries |
194 diary-bahai-mark-entries) | 194 diary-bahai-mark-entries) |
195 :group 'diary) | 195 :group 'diary) |
196 | 196 |
197 (defcustom print-diary-entries-hook 'lpr-buffer | 197 (defcustom print-diary-entries-hook 'lpr-buffer |
198 "List of functions called after a temporary diary buffer is prepared. | 198 "List of functions called after a temporary diary buffer is prepared. |
199 The buffer shows only the diary entries currently visible in the diary | 199 The buffer shows only the diary entries currently visible in the diary |
276 | 276 |
277 If the template is actually a function, it is called with the message | 277 If the template is actually a function, it is called with the message |
278 body text as argument, and may use `match-string' etc. to make a | 278 body text as argument, and may use `match-string' etc. to make a |
279 template following the rules above." | 279 template following the rules above." |
280 :type '(alist :key-type (regexp :tag "Regexp matching time/place") | 280 :type '(alist :key-type (regexp :tag "Regexp matching time/place") |
281 :value-type (choice | 281 :value-type (choice |
282 (string :tag "Template for entry") | 282 (string :tag "Template for entry") |
283 (function :tag | 283 (function :tag |
284 "Unary function providing template"))) | 284 "Unary function providing template"))) |
285 :version "22.1" | 285 :version "22.1" |
286 :group 'diary) | 286 :group 'diary) |
287 | 287 |
288 ;;; More user options below and in calendar.el. | 288 ;;; More user options below and in calendar.el. |
289 | 289 |
343 | 343 |
344 (defun diary-attrtype-convert (attrvalue type) | 344 (defun diary-attrtype-convert (attrvalue type) |
345 "Convert string ATTRVALUE to TYPE appropriate for a face description. | 345 "Convert string ATTRVALUE to TYPE appropriate for a face description. |
346 Valid TYPEs are: string, symbol, int, stringtnil, tnil." | 346 Valid TYPEs are: string, symbol, int, stringtnil, tnil." |
347 (cond ((eq type 'string) attrvalue) | 347 (cond ((eq type 'string) attrvalue) |
348 ((eq type 'symbol) (read attrvalue)) ; FIXME intern-soft? | 348 ((eq type 'symbol) (read attrvalue)) ; FIXME intern-soft? |
349 ((eq type 'int) (string-to-number attrvalue)) | 349 ((eq type 'int) (string-to-number attrvalue)) |
350 ((eq type 'stringtnil) | 350 ((eq type 'stringtnil) |
351 (cond ((string-equal "t" attrvalue) t) | 351 (cond ((string-equal "t" attrvalue) t) |
352 ((string-equal "nil" attrvalue) nil) | 352 ((string-equal "nil" attrvalue) nil) |
353 (t attrvalue))) | 353 (t attrvalue))) |
354 ((eq type 'tnil) (string-equal "t" attrvalue)))) | 354 ((eq type 'tnil) (string-equal "t" attrvalue)))) |
355 | 355 |
356 (defun diary-pull-attrs (entry fileglobattrs) | 356 (defun diary-pull-attrs (entry fileglobattrs) |
357 "Search for matches for regexps from `diary-face-attrs'. | 357 "Search for matches for regexps from `diary-face-attrs'. |
358 If ENTRY is nil, searches from the start of the current buffer, and | 358 If ENTRY is nil, searches from the start of the current buffer, and |
359 prepends all regexps with `diary-glob-file-regexp-prefix'. | 359 prepends all regexps with `diary-glob-file-regexp-prefix'. |
361 Returns a list of ENTRY followed by (ATTRIBUTE VALUE) pairs. | 361 Returns a list of ENTRY followed by (ATTRIBUTE VALUE) pairs. |
362 When ENTRY is non-nil, FILEGLOBATTRS forms the start of the (ATTRIBUTE VALUE) | 362 When ENTRY is non-nil, FILEGLOBATTRS forms the start of the (ATTRIBUTE VALUE) |
363 pairs." | 363 pairs." |
364 (let (regexp regnum attrname attrname attrvalue type ret-attr) | 364 (let (regexp regnum attrname attrname attrvalue type ret-attr) |
365 (if (null entry) | 365 (if (null entry) |
366 (save-excursion | 366 (save-excursion |
367 (dolist (attr diary-face-attrs) | 367 (dolist (attr diary-face-attrs) |
368 ;; FIXME inefficient searching. | 368 ;; FIXME inefficient searching. |
369 (goto-char (point-min)) | 369 (goto-char (point-min)) |
370 (setq regexp (concat diary-glob-file-regexp-prefix (car attr)) | 370 (setq regexp (concat diary-glob-file-regexp-prefix (car attr)) |
371 regnum (cadr attr) | 371 regnum (cadr attr) |
372 attrname (nth 2 attr) | 372 attrname (nth 2 attr) |
373 type (nth 3 attr) | 373 type (nth 3 attr) |
374 attrvalue (if (re-search-forward regexp nil t) | 374 attrvalue (if (re-search-forward regexp nil t) |
375 (match-string-no-properties regnum))) | 375 (match-string-no-properties regnum))) |
376 (and attrvalue | 376 (and attrvalue |
377 (setq attrvalue (diary-attrtype-convert attrvalue type)) | 377 (setq attrvalue (diary-attrtype-convert attrvalue type)) |
378 (setq ret-attr (append ret-attr | 378 (setq ret-attr (append ret-attr |
379 (list attrname attrvalue)))))) | 379 (list attrname attrvalue)))))) |
380 (setq ret-attr fileglobattrs) | 380 (setq ret-attr fileglobattrs) |
381 (dolist (attr diary-face-attrs) | 381 (dolist (attr diary-face-attrs) |
382 (setq regexp (car attr) | 382 (setq regexp (car attr) |
383 regnum (cadr attr) | 383 regnum (cadr attr) |
384 attrname (nth 2 attr) | 384 attrname (nth 2 attr) |
385 type (nth 3 attr) | 385 type (nth 3 attr) |
386 attrvalue nil) | 386 attrvalue nil) |
387 ;; FIXME multiple matches? | 387 ;; FIXME multiple matches? |
388 (if (string-match regexp entry) | 388 (if (string-match regexp entry) |
389 (setq attrvalue (match-string-no-properties regnum entry) | 389 (setq attrvalue (match-string-no-properties regnum entry) |
390 entry (replace-match "" t t entry))) | 390 entry (replace-match "" t t entry))) |
391 (and attrvalue | 391 (and attrvalue |
392 (setq attrvalue (diary-attrtype-convert attrvalue type)) | 392 (setq attrvalue (diary-attrtype-convert attrvalue type)) |
393 (setq ret-attr (append ret-attr (list attrname attrvalue)))))) | 393 (setq ret-attr (append ret-attr (list attrname attrvalue)))))) |
394 (list entry ret-attr))) | 394 (list entry ret-attr))) |
395 | 395 |
396 ;;;###cal-autoload | 396 ;;;###cal-autoload |
397 (defun diary-set-maybe-redraw (symbol value) | 397 (defun diary-set-maybe-redraw (symbol value) |
398 "Set SYMBOL's value to VALUE, and redraw the diary if necessary. | 398 "Set SYMBOL's value to VALUE, and redraw the diary if necessary. |
469 | 469 |
470 This variable does not affect the diary display with the `d' command | 470 This variable does not affect the diary display with the `d' command |
471 from the calendar; in that case, the prefix argument controls the | 471 from the calendar; in that case, the prefix argument controls the |
472 number of days of diary entries displayed." | 472 number of days of diary entries displayed." |
473 :type '(choice (integer :tag "Entries") | 473 :type '(choice (integer :tag "Entries") |
474 (vector :value [0 0 0 0 0 0 0] | 474 (vector :value [0 0 0 0 0 0 0] |
475 (integer :tag "Sunday") | 475 (integer :tag "Sunday") |
476 (integer :tag "Monday") | 476 (integer :tag "Monday") |
477 (integer :tag "Tuesday") | 477 (integer :tag "Tuesday") |
478 (integer :tag "Wednesday") | 478 (integer :tag "Wednesday") |
479 (integer :tag "Thursday") | 479 (integer :tag "Thursday") |
480 (integer :tag "Friday") | 480 (integer :tag "Friday") |
481 (integer :tag "Saturday"))) | 481 (integer :tag "Saturday"))) |
482 :initialize 'custom-initialize-default | 482 :initialize 'custom-initialize-default |
483 :set 'diary-set-maybe-redraw | 483 :set 'diary-set-maybe-redraw |
484 :group 'diary) | 484 :group 'diary) |
485 | 485 |
486 | 486 |
488 "Function applied to entry string before putting it into the entries list. | 488 "Function applied to entry string before putting it into the entries list. |
489 Can be used by programs integrating a diary list into other buffers (e.g. | 489 Can be used by programs integrating a diary list into other buffers (e.g. |
490 org.el and planner.el) to modify the string or add properties to it. | 490 org.el and planner.el) to modify the string or add properties to it. |
491 The function takes a string argument and must return a string.") | 491 The function takes a string argument and must return a string.") |
492 | 492 |
493 (defvar diary-entries-list) ; bound in diary-list-entries | 493 (defvar diary-entries-list) ; bound in diary-list-entries |
494 | 494 |
495 (defun add-to-diary-list (date string specifier &optional marker | 495 (defun add-to-diary-list (date string specifier &optional marker |
496 globcolor literal) | 496 globcolor literal) |
497 "Add an entry to `diary-entries-list'. | 497 "Add an entry to `diary-entries-list'. |
498 Do nothing if DATE or STRING is nil. DATE is the (MONTH DAY | 498 Do nothing if DATE or STRING is nil. DATE is the (MONTH DAY |
511 (let ((prefix (funcall diary-file-name-prefix-function | 511 (let ((prefix (funcall diary-file-name-prefix-function |
512 (buffer-file-name)))) | 512 (buffer-file-name)))) |
513 (or (string-equal prefix "") | 513 (or (string-equal prefix "") |
514 (setq string (format "[%s] %s" prefix string))))) | 514 (setq string (format "[%s] %s" prefix string))))) |
515 (and diary-modify-entry-list-string-function | 515 (and diary-modify-entry-list-string-function |
516 (setq string (funcall diary-modify-entry-list-string-function | 516 (setq string (funcall diary-modify-entry-list-string-function |
517 string))) | 517 string))) |
518 (setq diary-entries-list | 518 (setq diary-entries-list |
519 (append diary-entries-list | 519 (append diary-entries-list |
520 (list (list date string specifier | 520 (list (list date string specifier |
521 (list marker (buffer-file-name) literal) | 521 (list marker (buffer-file-name) literal) |
522 globcolor)))))) | 522 globcolor)))))) |
565 (unless number | 565 (unless number |
566 (setq number (if (vectorp number-of-diary-entries) | 566 (setq number (if (vectorp number-of-diary-entries) |
567 (aref number-of-diary-entries (calendar-day-of-week date)) | 567 (aref number-of-diary-entries (calendar-day-of-week date)) |
568 number-of-diary-entries))) | 568 number-of-diary-entries))) |
569 (when (> number 0) | 569 (when (> number 0) |
570 (let ((original-date date) ; save for possible use in the hooks | 570 (let ((original-date date) ; save for possible use in the hooks |
571 diary-entries-list | 571 diary-entries-list |
572 file-glob-attrs | 572 file-glob-attrs |
573 (date-string (calendar-date-string date)) | 573 (date-string (calendar-date-string date)) |
574 (d-file (substitute-in-file-name diary-file))) | 574 (d-file (substitute-in-file-name diary-file))) |
575 (message "Preparing diary...") | 575 (message "Preparing diary...") |
609 (day (extract-calendar-day date)) | 609 (day (extract-calendar-day date)) |
610 (year (extract-calendar-year date)) | 610 (year (extract-calendar-year date)) |
611 (entry-found (list-sexp-diary-entries date))) | 611 (entry-found (list-sexp-diary-entries date))) |
612 (dolist (date-form diary-date-forms) | 612 (dolist (date-form diary-date-forms) |
613 (let* ((backup (when (eq (car date-form) 'backup) | 613 (let* ((backup (when (eq (car date-form) 'backup) |
614 (setq date-form (cdr date-form)) | 614 (setq date-form (cdr date-form)) |
615 t)) | 615 t)) |
616 (dayname | 616 (dayname |
617 (format "%s\\|%s\\.?" | 617 (format "%s\\|%s\\.?" |
618 (calendar-day-name date) | 618 (calendar-day-name date) |
619 (calendar-day-name date 'abbrev))) | 619 (calendar-day-name date 'abbrev))) |
620 (monthname | 620 (monthname |
621 (format "\\*\\|%s\\|%s\\.?" | 621 (format "\\*\\|%s\\|%s\\.?" |
622 (calendar-month-name month) | 622 (calendar-month-name month) |
623 (calendar-month-name month 'abbrev))) | 623 (calendar-month-name month 'abbrev))) |
624 (month (concat "\\*\\|0*" (int-to-string month))) | 624 (month (concat "\\*\\|0*" (int-to-string month))) |
625 (day (concat "\\*\\|0*" (int-to-string day))) | 625 (day (concat "\\*\\|0*" (int-to-string day))) |
626 (year | 626 (year |
627 (concat | 627 (concat |
628 "\\*\\|0*" (int-to-string year) | 628 "\\*\\|0*" (int-to-string year) |
629 (if abbreviated-calendar-year | 629 (if abbreviated-calendar-year |
630 (concat "\\|" (format "%02d" (% year 100))) | 630 (concat "\\|" (format "%02d" (% year 100))) |
631 ""))) | 631 ""))) |
632 (regexp | 632 (regexp |
633 (concat | 633 (concat |
634 "^" mark "?\\(" | 634 "^" mark "?\\(" |
635 ;; This must be let* so that date-form | 635 ;; This must be let* so that date-form |
636 ;; can use day etc. | 636 ;; can use day etc. |
637 (mapconcat 'eval date-form "\\)\\(?:") | 637 (mapconcat 'eval date-form "\\)\\(?:") |
638 "\\)")) | 638 "\\)")) |
639 (case-fold-search t)) | 639 (case-fold-search t)) |
640 (goto-char (point-min)) | 640 (goto-char (point-min)) |
641 (while (re-search-forward regexp nil t) | 641 (while (re-search-forward regexp nil t) |
642 (if backup (re-search-backward "\\<" nil t)) | 642 (if backup (re-search-backward "\\<" nil t)) |
643 (if (and (bolp) (not (looking-at "[ \t]"))) | 643 (if (and (bolp) (not (looking-at "[ \t]"))) |
644 ;; Diary entry that consists only of date. | 644 ;; Diary entry that consists only of date. |
645 (backward-char 1) | 645 (backward-char 1) |
646 ;; Found a nonempty diary entry--make it | 646 ;; Found a nonempty diary entry--make it |
647 ;; visible and add it to the list. | 647 ;; visible and add it to the list. |
648 (setq entry-found t) | 648 (setq entry-found t) |
649 (if (looking-at "[ \t]*\n[ \t]") (forward-line 1)) | 649 (if (looking-at "[ \t]*\n[ \t]") (forward-line 1)) |
650 (let ((entry-start (point)) | 650 (let ((entry-start (point)) |
651 date-start temp) | 651 date-start temp) |
652 (setq date-start | 652 (setq date-start |
653 (line-end-position | 653 (line-end-position |
654 (if (and (bolp) (> number 1)) -1 0))) | 654 (if (and (bolp) (> number 1)) -1 0))) |
655 (forward-line 1) | 655 (forward-line 1) |
656 (while (looking-at "[ \t]") | 656 (while (looking-at "[ \t]") |
657 (forward-line 1)) | 657 (forward-line 1)) |
658 (unless (and (eobp) (not (bolp))) | 658 (unless (and (eobp) (not (bolp))) |
659 (backward-char 1)) | 659 (backward-char 1)) |
660 (unless list-only | 660 (unless list-only |
661 (remove-overlays date-start (point) | 661 (remove-overlays date-start (point) |
662 'invisible 'diary)) | 662 'invisible 'diary)) |
663 (setq temp (diary-pull-attrs | 663 (setq temp (diary-pull-attrs |
664 (buffer-substring entry-start (point)) | 664 (buffer-substring entry-start (point)) |
665 file-glob-attrs)) | 665 file-glob-attrs)) |
666 (add-to-diary-list | 666 (add-to-diary-list |
667 date | 667 date |
668 (car temp) | 668 (car temp) |
669 (buffer-substring | 669 (buffer-substring |
670 (1+ date-start) (1- entry-start)) | 670 (1+ date-start) (1- entry-start)) |
679 (goto-char (point-min)) | 679 (goto-char (point-min)) |
680 (run-hooks 'nongregorian-diary-listing-hook | 680 (run-hooks 'nongregorian-diary-listing-hook |
681 'list-diary-entries-hook) | 681 'list-diary-entries-hook) |
682 (unless list-only | 682 (unless list-only |
683 (if diary-display-hook | 683 (if diary-display-hook |
684 (run-hooks 'diary-display-hook) | 684 (run-hooks 'diary-display-hook) |
685 (simple-diary-display))) | 685 (simple-diary-display))) |
686 (run-hooks 'diary-hook) | 686 (run-hooks 'diary-hook) |
687 diary-entries-list)))))) | 687 diary-entries-list)))))) |
688 | 688 |
689 (defun diary-unhide-everything () | 689 (defun diary-unhide-everything () |
690 "Show all invisible text in the diary." | 690 "Show all invisible text in the diary." |
691 (kill-local-variable 'diary-selective-display) | 691 (kill-local-variable 'diary-selective-display) |
692 (remove-overlays (point-min) (point-max) 'invisible 'diary) | 692 (remove-overlays (point-min) (point-max) 'invisible 'diary) |
693 (kill-local-variable 'mode-line-format)) | 693 (kill-local-variable 'mode-line-format)) |
694 | 694 |
695 (defvar original-date) ; bound in diary-list-entries | 695 (defvar original-date) ; bound in diary-list-entries |
696 (defvar number) | 696 (defvar number) |
697 | 697 |
698 (defun include-other-diary-files () | 698 (defun include-other-diary-files () |
699 "Include the diary entries from other diary files with those of `diary-file'. | 699 "Include the diary entries from other diary files with those of `diary-file'. |
700 This function is suitable for use in `list-diary-entries-hook'; | 700 This function is suitable for use in `list-diary-entries-hook'; |
710 "^" | 710 "^" |
711 (regexp-quote diary-include-string) | 711 (regexp-quote diary-include-string) |
712 " \"\\([^\"]*\\)\"") | 712 " \"\\([^\"]*\\)\"") |
713 nil t) | 713 nil t) |
714 (let ((diary-file (substitute-in-file-name | 714 (let ((diary-file (substitute-in-file-name |
715 (match-string-no-properties 1))) | 715 (match-string-no-properties 1))) |
716 (diary-list-include-blanks nil) | 716 (diary-list-include-blanks nil) |
717 (list-diary-entries-hook 'include-other-diary-files) | 717 (list-diary-entries-hook 'include-other-diary-files) |
718 (diary-display-hook 'ignore) | 718 (diary-display-hook 'ignore) |
719 (diary-hook nil)) | 719 (diary-hook nil)) |
720 (if (file-exists-p diary-file) | 720 (if (file-exists-p diary-file) |
721 (if (file-readable-p diary-file) | 721 (if (file-readable-p diary-file) |
722 (unwind-protect | 722 (unwind-protect |
723 (setq diary-entries-list | 723 (setq diary-entries-list |
724 (append diary-entries-list | 724 (append diary-entries-list |
729 (message "Can't read included diary file %s" diary-file) | 729 (message "Can't read included diary file %s" diary-file) |
730 (sleep-for 2)) | 730 (sleep-for 2)) |
731 (beep) | 731 (beep) |
732 (message "Can't find included diary file %s" diary-file) | 732 (message "Can't find included diary file %s" diary-file) |
733 (sleep-for 2)))) | 733 (sleep-for 2)))) |
734 (goto-char (point-min))) | 734 (goto-char (point-min))) |
735 | 735 |
736 ;; Bound in diary-list-entries. | 736 ;; Bound in diary-list-entries. |
737 (defvar date-string) | 737 (defvar date-string) |
738 (defvar diary-saved-point) | 738 (defvar diary-saved-point) |
739 | 739 |
773 (set-window-point window diary-saved-point) | 773 (set-window-point window diary-saved-point) |
774 (set-window-start window (point-min)))) | 774 (set-window-start window (point-min)))) |
775 (message "Preparing diary...done")))) | 775 (message "Preparing diary...done")))) |
776 | 776 |
777 (defface diary-button '((((type pc) (class color)) | 777 (defface diary-button '((((type pc) (class color)) |
778 (:foreground "lightblue"))) | 778 (:foreground "lightblue"))) |
779 "Default face used for buttons." | 779 "Default face used for buttons." |
780 :version "22.1" | 780 :version "22.1" |
781 :group 'diary) | 781 :group 'diary) |
782 ;; Backward-compatibility alias. FIXME make obsolete. | 782 ;; Backward-compatibility alias. FIXME make obsolete. |
783 (put 'diary-button-face 'face-alias 'diary-button) | 783 (put 'diary-button-face 'face-alias 'diary-button) |
843 (let ((entry-list diary-entries-list) | 843 (let ((entry-list diary-entries-list) |
844 (holiday-list) | 844 (holiday-list) |
845 (holiday-list-last-month 1) | 845 (holiday-list-last-month 1) |
846 (holiday-list-last-year 1) | 846 (holiday-list-last-year 1) |
847 (date (list 0 0 0))) | 847 (date (list 0 0 0))) |
848 (dolist (entry entry-list) | 848 (dolist (entry entry-list) |
849 (if (not (calendar-date-equal date (car entry))) | 849 (if (not (calendar-date-equal date (car entry))) |
850 (progn | 850 (progn |
851 (setq date (car entry)) | 851 (setq date (car entry)) |
852 (and holidays-in-diary-buffer | 852 (and holidays-in-diary-buffer |
853 (calendar-date-compare | 853 (calendar-date-compare |
858 holiday-list-last-year)) | 858 holiday-list-last-year)) |
859 (list date)) | 859 (list date)) |
860 ;; We need to get the holidays for the next 3 months. | 860 ;; We need to get the holidays for the next 3 months. |
861 (setq holiday-list-last-month | 861 (setq holiday-list-last-month |
862 (extract-calendar-month date) | 862 (extract-calendar-month date) |
863 holiday-list-last-year | 863 holiday-list-last-year |
864 (extract-calendar-year date)) | 864 (extract-calendar-year date)) |
865 (progn | 865 (progn |
866 (increment-calendar-month | 866 (increment-calendar-month |
867 holiday-list-last-month holiday-list-last-year 1) | 867 holiday-list-last-month holiday-list-last-year 1) |
868 t) | 868 t) |
871 (displayed-year holiday-list-last-year)) | 871 (displayed-year holiday-list-last-year)) |
872 (calendar-holiday-list))) | 872 (calendar-holiday-list))) |
873 (increment-calendar-month | 873 (increment-calendar-month |
874 holiday-list-last-month holiday-list-last-year 1)) | 874 holiday-list-last-month holiday-list-last-year 1)) |
875 (let (date-holiday-list) | 875 (let (date-holiday-list) |
876 ;; Make a list of all holidays for date. | 876 ;; Make a list of all holidays for date. |
877 (dolist (h holiday-list) | 877 (dolist (h holiday-list) |
878 (if (calendar-date-equal date (car h)) | 878 (if (calendar-date-equal date (car h)) |
879 (setq date-holiday-list (append date-holiday-list | 879 (setq date-holiday-list (append date-holiday-list |
880 (cdr h))))) | 880 (cdr h))))) |
881 (insert (if (bobp) "" ?\n) (calendar-date-string date)) | 881 (insert (if (bobp) "" ?\n) (calendar-date-string date)) |
882 (if date-holiday-list (insert ": ")) | 882 (if date-holiday-list (insert ": ")) |
883 (let ((l (current-column)) | 883 (let ((l (current-column)) |
884 (longest 0)) | 884 (longest 0)) |
885 (insert (mapconcat (lambda (x) | 885 (insert (mapconcat (lambda (x) |
886 (if (< longest (length x)) | 886 (if (< longest (length x)) |
887 (setq longest (length x))) | 887 (setq longest (length x))) |
888 x) | 888 x) |
889 date-holiday-list | 889 date-holiday-list |
890 (concat "\n" (make-string l ? )))) | 890 (concat "\n" (make-string l ? )))) |
891 (insert ?\n (make-string (+ l longest) ?=) ?\n))))) | 891 (insert ?\n (make-string (+ l longest) ?=) ?\n))))) |
892 (let ((this-entry (cadr entry)) | 892 (let ((this-entry (cadr entry)) |
893 this-loc) | 893 this-loc) |
894 (unless (zerop (length this-entry)) | 894 (unless (zerop (length this-entry)) |
895 (if (setq this-loc (nth 3 entry)) | 895 (if (setq this-loc (nth 3 entry)) |
896 (insert-button (concat this-entry "\n") | 896 (insert-button (concat this-entry "\n") |
897 ;; (MARKER FILENAME SPECIFIER LITERAL) | 897 ;; (MARKER FILENAME SPECIFIER LITERAL) |
898 'locator (list (car this-loc) | 898 'locator (list (car this-loc) |
899 (cadr this-loc) | 899 (cadr this-loc) |
900 (nth 2 entry) | 900 (nth 2 entry) |
901 (or (nth 2 this-loc) | 901 (or (nth 2 this-loc) |
902 (nth 1 entry))) | 902 (nth 1 entry))) |
903 :type 'diary-entry) | 903 :type 'diary-entry) |
904 (insert this-entry ?\n)) | 904 (insert this-entry ?\n)) |
905 (save-excursion | 905 (save-excursion |
906 (let* ((marks (nth 4 entry)) | 906 (let* ((marks (nth 4 entry)) |
907 (faceinfo marks) | 907 (faceinfo marks) |
908 temp-face) | 908 temp-face) |
909 (when marks | 909 (when marks |
910 (setq temp-face (make-symbol | 910 (setq temp-face (make-symbol |
911 (apply | 911 (apply |
912 'concat "temp-face-" | 912 'concat "temp-face-" |
913 (mapcar (lambda (sym) | 913 (mapcar (lambda (sym) |
914 (if (stringp sym) | 914 (if (stringp sym) |
915 sym | 915 sym |
916 (symbol-name sym))) | 916 (symbol-name sym))) |
917 marks)))) | 917 marks)))) |
918 (make-face temp-face) | 918 (make-face temp-face) |
919 ;; Remove :face info from the marks, | 919 ;; Remove :face info from the marks, |
920 ;; copy the face info into temp-face | 920 ;; copy the face info into temp-face |
921 (while (setq faceinfo (memq :face faceinfo)) | 921 (while (setq faceinfo (memq :face faceinfo)) |
922 (copy-face (read (nth 1 faceinfo)) temp-face) | 922 (copy-face (read (nth 1 faceinfo)) temp-face) |
923 (setcar faceinfo nil) | 923 (setcar faceinfo nil) |
924 (setcar (cdr faceinfo) nil)) | 924 (setcar (cdr faceinfo) nil)) |
925 (setq marks (delq nil marks)) | 925 (setq marks (delq nil marks)) |
926 ;; Apply the font aspects. | 926 ;; Apply the font aspects. |
927 (apply 'set-face-attribute temp-face nil marks) | 927 (apply 'set-face-attribute temp-face nil marks) |
928 (search-backward this-entry) | 928 (search-backward this-entry) |
929 (overlay-put | 929 (overlay-put |
930 (make-overlay (match-beginning 0) (match-end 0)) | 930 (make-overlay (match-beginning 0) (match-end 0)) |
931 'face temp-face)))))))) | 931 'face temp-face)))))))) |
932 (set-buffer-modified-p nil) | 932 (set-buffer-modified-p nil) |
933 (goto-char (point-min)) | 933 (goto-char (point-min)) |
934 (setq buffer-read-only t) | 934 (setq buffer-read-only t) |
935 (display-buffer fancy-diary-buffer) | 935 (display-buffer fancy-diary-buffer) |
936 (fancy-diary-display-mode) | 936 (fancy-diary-display-mode) |
1164 (- y 100) | 1164 (- y 100) |
1165 (if (> (- current-y y) 50) | 1165 (if (> (- current-y y) 50) |
1166 (+ y 100) | 1166 (+ y 100) |
1167 y))) | 1167 y))) |
1168 (string-to-number y-str))))) | 1168 (string-to-number y-str))))) |
1169 (setq marks (nth 1 | 1169 (setq marks (nth 1 |
1170 (diary-pull-attrs | 1170 (diary-pull-attrs |
1171 (buffer-substring-no-properties | 1171 (buffer-substring-no-properties |
1172 (point) (line-end-position)) | 1172 (point) (line-end-position)) |
1173 file-glob-attrs))) | 1173 file-glob-attrs))) |
1174 (if dd-name | 1174 (if dd-name |
1175 (mark-calendar-days-named | 1175 (mark-calendar-days-named |
1176 (cdr (assoc-string | 1176 (cdr (assoc-string |
1177 dd-name | 1177 dd-name |
1178 (calendar-make-alist | 1178 (calendar-make-alist |
1190 (mark-sexp-diary-entries) | 1190 (mark-sexp-diary-entries) |
1191 (run-hooks 'nongregorian-diary-marking-hook | 1191 (run-hooks 'nongregorian-diary-marking-hook |
1192 'mark-diary-entries-hook)) | 1192 'mark-diary-entries-hook)) |
1193 (message "Marking diary entries...done"))))) | 1193 (message "Marking diary entries...done"))))) |
1194 | 1194 |
1195 (defvar displayed-year) ; bound in generate-calendar | 1195 (defvar displayed-year) ; bound in generate-calendar |
1196 (defvar displayed-month) | 1196 (defvar displayed-month) |
1197 | 1197 |
1198 (defun mark-sexp-diary-entries () | 1198 (defun mark-sexp-diary-entries () |
1199 "Mark days in the calendar window that have sexp diary entries. | 1199 "Mark days in the calendar window that have sexp diary entries. |
1200 Each entry in the diary file (or included files) visible in the calendar window | 1200 Each entry in the diary file (or included files) visible in the calendar window |
1224 sexp entry entry-start marks) | 1224 sexp entry entry-start marks) |
1225 (forward-sexp) | 1225 (forward-sexp) |
1226 (setq sexp (buffer-substring-no-properties sexp-start (point))) | 1226 (setq sexp (buffer-substring-no-properties sexp-start (point))) |
1227 (forward-char 1) | 1227 (forward-char 1) |
1228 (if (and (bolp) (not (looking-at "[ \t]"))) | 1228 (if (and (bolp) (not (looking-at "[ \t]"))) |
1229 ;; Diary entry consists only of the sexp. | 1229 ;; Diary entry consists only of the sexp. |
1230 (progn | 1230 (progn |
1231 (backward-char 1) | 1231 (backward-char 1) |
1232 (setq entry "")) | 1232 (setq entry "")) |
1233 (setq entry-start (point)) | 1233 (setq entry-start (point)) |
1234 ;; Find end of entry. | 1234 ;; Find end of entry. |
1236 (while (looking-at "[ \t]") | 1236 (while (looking-at "[ \t]") |
1237 (forward-line 1)) | 1237 (forward-line 1)) |
1238 (if (bolp) (backward-char 1)) | 1238 (if (bolp) (backward-char 1)) |
1239 (setq entry (buffer-substring-no-properties entry-start (point)))) | 1239 (setq entry (buffer-substring-no-properties entry-start (point)))) |
1240 (calendar-for-loop date from first-date to last-date do | 1240 (calendar-for-loop date from first-date to last-date do |
1241 (if (setq mark (diary-sexp-entry sexp entry | 1241 (if (setq mark (diary-sexp-entry sexp entry |
1242 (calendar-gregorian-from-absolute date))) | 1242 (calendar-gregorian-from-absolute date))) |
1243 (progn | 1243 (progn |
1244 (setq marks (diary-pull-attrs entry file-glob-attrs) | 1244 (setq marks (diary-pull-attrs entry file-glob-attrs) |
1245 marks (nth 1 (diary-pull-attrs entry file-glob-attrs))) | 1245 marks (nth 1 (diary-pull-attrs entry file-glob-attrs))) |
1246 (mark-visible-calendar-date | 1246 (mark-visible-calendar-date |
1247 (calendar-gregorian-from-absolute date) | 1247 (calendar-gregorian-from-absolute date) |
1248 (if (< 0 (length marks)) | 1248 (if (< 0 (length marks)) |
1249 marks | 1249 marks |
1250 (if (consp mark) | 1250 (if (consp mark) |
1251 (car mark))))))))))) | 1251 (car mark))))))))))) |
1252 | 1252 |
1253 (defun mark-included-diary-files () | 1253 (defun mark-included-diary-files () |
1254 "Mark the diary entries from other diary files with those of the diary file. | 1254 "Mark the diary entries from other diary files with those of the diary file. |
1255 This function is suitable for use as the `mark-diary-entries-hook'; it enables | 1255 This function is suitable for use as the `mark-diary-entries-hook'; it enables |
1256 you to use shared diary files together with your own. The files included are | 1256 you to use shared diary files together with your own. The files included are |
1297 (day)) | 1297 (day)) |
1298 (increment-calendar-month succ-month succ-year 1) | 1298 (increment-calendar-month succ-month succ-year 1) |
1299 (increment-calendar-month prev-month prev-year -1) | 1299 (increment-calendar-month prev-month prev-year -1) |
1300 (setq day (calendar-absolute-from-gregorian | 1300 (setq day (calendar-absolute-from-gregorian |
1301 (calendar-nth-named-day 1 dayname prev-month prev-year)) | 1301 (calendar-nth-named-day 1 dayname prev-month prev-year)) |
1302 last-day (calendar-absolute-from-gregorian | 1302 last-day (calendar-absolute-from-gregorian |
1303 (calendar-nth-named-day -1 dayname succ-month succ-year))) | 1303 (calendar-nth-named-day -1 dayname succ-month succ-year))) |
1304 (while (<= day last-day) | 1304 (while (<= day last-day) |
1305 (mark-visible-calendar-date (calendar-gregorian-from-absolute day) | 1305 (mark-visible-calendar-date (calendar-gregorian-from-absolute day) |
1306 color) | 1306 color) |
1307 (setq day (+ day 7)))))) | 1307 (setq day (+ day 7)))))) |
1308 | 1308 |
1309 (defun mark-calendar-date-pattern (month day year &optional color) | 1309 (defun mark-calendar-date-pattern (month day year &optional color) |
1310 "Mark all dates in the calendar window that conform to MONTH/DAY/YEAR. | 1310 "Mark all dates in the calendar window that conform to MONTH/DAY/YEAR. |
1311 A value of 0 in any position is a wildcard. | 1311 A value of 0 in any position is a wildcard. |
1326 (or (zerop p-year) (= year p-year))) | 1326 (or (zerop p-year) (= year p-year))) |
1327 (and (zerop p-month) | 1327 (and (zerop p-month) |
1328 (or (zerop p-year) (= year p-year)))) | 1328 (or (zerop p-year) (= year p-year)))) |
1329 (if (zerop p-day) | 1329 (if (zerop p-day) |
1330 (calendar-for-loop | 1330 (calendar-for-loop |
1331 i from 1 to (calendar-last-day-of-month month year) do | 1331 i from 1 to (calendar-last-day-of-month month year) do |
1332 (mark-visible-calendar-date (list month i year) color)) | 1332 (mark-visible-calendar-date (list month i year) color)) |
1333 (mark-visible-calendar-date (list month p-day year) color)))) | 1333 (mark-visible-calendar-date (list month p-day year) color)))) |
1334 | 1334 |
1335 (defun sort-diary-entries () | 1335 (defun sort-diary-entries () |
1336 "Sort the list of diary entries by time of day." | 1336 "Sort the list of diary entries by time of day." |
1337 (setq diary-entries-list (sort diary-entries-list 'diary-entry-compare))) | 1337 (setq diary-entries-list (sort diary-entries-list 'diary-entry-compare))) |
1353 Returns `diary-unknown-time' (default value -9999) if no time is recognized. | 1353 Returns `diary-unknown-time' (default value -9999) if no time is recognized. |
1354 The recognized forms are XXXX, X:XX, or XX:XX (military time), and XXam, | 1354 The recognized forms are XXXX, X:XX, or XX:XX (military time), and XXam, |
1355 XXAM, XXpm, XXPM, XX:XXam, XX:XXAM XX:XXpm, or XX:XXPM. A period (.) can | 1355 XXAM, XXpm, XXPM, XX:XXam, XX:XXAM XX:XXpm, or XX:XXPM. A period (.) can |
1356 be used instead of a colon (:) to separate the hour and minute parts." | 1356 be used instead of a colon (:) to separate the hour and minute parts." |
1357 (let ((case-fold-search nil)) | 1357 (let ((case-fold-search nil)) |
1358 (cond ((string-match ; military time | 1358 (cond ((string-match ; military time |
1359 "\\`[ \t\n]*\\([0-9]?[0-9]\\)[:.]?\\([0-9][0-9]\\)\\(\\>\\|[^ap]\\)" | 1359 "\\`[ \t\n]*\\([0-9]?[0-9]\\)[:.]?\\([0-9][0-9]\\)\\(\\>\\|[^ap]\\)" |
1360 s) | 1360 s) |
1361 (+ (* 100 (string-to-number (match-string 1 s))) | 1361 (+ (* 100 (string-to-number (match-string 1 s))) |
1362 (string-to-number (match-string 2 s)))) | 1362 (string-to-number (match-string 2 s)))) |
1363 ((string-match ; hour only (XXam or XXpm) | 1363 ((string-match ; hour only (XXam or XXpm) |
1364 "\\`[ \t\n]*\\([0-9]?[0-9]\\)\\([ap]\\)m\\>" s) | 1364 "\\`[ \t\n]*\\([0-9]?[0-9]\\)\\([ap]\\)m\\>" s) |
1365 (+ (* 100 (% (string-to-number (match-string 1 s)) 12)) | 1365 (+ (* 100 (% (string-to-number (match-string 1 s)) 12)) |
1366 (if (equal ?a (downcase (aref s (match-beginning 2)))) | 1366 (if (equal ?a (downcase (aref s (match-beginning 2)))) |
1367 0 1200))) | 1367 0 1200))) |
1368 ((string-match ; hour and minute (XX:XXam or XX:XXpm) | 1368 ((string-match ; hour and minute (XX:XXam or XX:XXpm) |
1369 "\\`[ \t\n]*\\([0-9]?[0-9]\\)[:.]\\([0-9][0-9]\\)\\([ap]\\)m\\>" s) | 1369 "\\`[ \t\n]*\\([0-9]?[0-9]\\)[:.]\\([0-9][0-9]\\)\\([ap]\\)m\\>" s) |
1370 (+ (* 100 (% (string-to-number (match-string 1 s)) 12)) | 1370 (+ (* 100 (% (string-to-number (match-string 1 s)) 12)) |
1371 (string-to-number (match-string 2 s)) | 1371 (string-to-number (match-string 2 s)) |
1372 (if (equal ?a (downcase (aref s (match-beginning 3)))) | 1372 (if (equal ?a (downcase (aref s (match-beginning 3)))) |
1373 0 1200))) | 1373 0 1200))) |
1374 (t diary-unknown-time)))) ; unrecognizable | 1374 (t diary-unknown-time)))) ; unrecognizable |
1375 | 1375 |
1376 (defun list-sexp-diary-entries (date) | 1376 (defun list-sexp-diary-entries (date) |
1377 "Add sexp entries for DATE from the diary file to `diary-entries-list'. | 1377 "Add sexp entries for DATE from the diary file to `diary-entries-list'. |
1378 Also, make them visible in the diary file. Returns t if any entries were | 1378 Also, make them visible in the diary file. Returns t if any entries were |
1379 found. | 1379 found. |
1555 (setq specifier | 1555 (setq specifier |
1556 (buffer-substring-no-properties (1+ line-start) (point)) | 1556 (buffer-substring-no-properties (1+ line-start) (point)) |
1557 entry-start (1+ line-start)) | 1557 entry-start (1+ line-start)) |
1558 (forward-char 1) | 1558 (forward-char 1) |
1559 (if (and (bolp) (not (looking-at "[ \t]"))) | 1559 (if (and (bolp) (not (looking-at "[ \t]"))) |
1560 ;; Diary entry consists only of the sexp. | 1560 ;; Diary entry consists only of the sexp. |
1561 (progn | 1561 (progn |
1562 (backward-char 1) | 1562 (backward-char 1) |
1563 (setq entry "")) | 1563 (setq entry "")) |
1564 (setq entry-start (point)) | 1564 (setq entry-start (point)) |
1565 (forward-line 1) | 1565 (forward-line 1) |
1602 (message "Bad sexp at line %d in %s: %s" | 1602 (message "Bad sexp at line %d in %s: %s" |
1603 (count-lines (point-min) (point)) | 1603 (count-lines (point-min) (point)) |
1604 diary-file sexp) | 1604 diary-file sexp) |
1605 (sleep-for 2)))))) | 1605 (sleep-for 2)))))) |
1606 (cond ((stringp result) result) | 1606 (cond ((stringp result) result) |
1607 ((and (consp result) | 1607 ((and (consp result) |
1608 (stringp (cdr result))) result) | 1608 (stringp (cdr result))) result) |
1609 (result entry) | 1609 (result entry) |
1610 (t nil)))) | 1610 (t nil)))) |
1611 | 1611 |
1612 (defvar date) | 1612 (defvar date) |
1613 (defvar entry) | 1613 (defvar entry) |
1614 | 1614 |
1674 backward from the end of the month. | 1674 backward from the end of the month. |
1675 | 1675 |
1676 An optional parameter DAY means the Nth DAYNAME on or after/before MONTH DAY. | 1676 An optional parameter DAY means the Nth DAYNAME on or after/before MONTH DAY. |
1677 Optional MARK specifies a face or single-character string to use when | 1677 Optional MARK specifies a face or single-character string to use when |
1678 highlighting the day in the calendar." | 1678 highlighting the day in the calendar." |
1679 ;; This is messy because the diary entry may apply, but the date on which it | 1679 ;; This is messy because the diary entry may apply, but the date on which it |
1680 ;; is based can be in a different month/year. For example, asking for the | 1680 ;; is based can be in a different month/year. For example, asking for the |
1681 ;; first Monday after December 30. For large values of |n| the problem is | 1681 ;; first Monday after December 30. For large values of |n| the problem is |
1682 ;; more grotesque. | 1682 ;; more grotesque. |
1683 (and (= dayname (calendar-day-of-week date)) | 1683 (and (= dayname (calendar-day-of-week date)) |
1684 (let* ((m (extract-calendar-month date)) | 1684 (let* ((m (extract-calendar-month date)) |
1685 (d (extract-calendar-day date)) | 1685 (d (extract-calendar-day date)) |
1686 (y (extract-calendar-year date)) | 1686 (y (extract-calendar-year date)) |
1687 ;; Last (n>0) or first (n<0) possible base date for entry. | 1687 ;; Last (n>0) or first (n<0) possible base date for entry. |
1688 (limit | 1688 (limit |
1689 (calendar-nth-named-absday (- n) dayname m y d)) | 1689 (calendar-nth-named-absday (- n) dayname m y d)) |
1690 (last-abs (if (> n 0) limit (+ limit 6))) | 1690 (last-abs (if (> n 0) limit (+ limit 6))) |
1691 (first-abs (if (> n 0) (- limit 6) limit)) | 1691 (first-abs (if (> n 0) (- limit 6) limit)) |
1692 (last (calendar-gregorian-from-absolute last-abs)) | 1692 (last (calendar-gregorian-from-absolute last-abs)) |
1697 (y1 (extract-calendar-year first)) | 1697 (y1 (extract-calendar-year first)) |
1698 ;; m2, d2 is last possible base date. | 1698 ;; m2, d2 is last possible base date. |
1699 (m2 (extract-calendar-month last)) | 1699 (m2 (extract-calendar-month last)) |
1700 (d2 (extract-calendar-day last)) | 1700 (d2 (extract-calendar-day last)) |
1701 (y2 (extract-calendar-year last))) | 1701 (y2 (extract-calendar-year last))) |
1702 (if (or (and (= m1 m2) ; only possible base dates in one month | 1702 (if (or (and (= m1 m2) ; only possible base dates in one month |
1703 (or (eq month t) | 1703 (or (eq month t) |
1704 (if (listp month) | 1704 (if (listp month) |
1705 (memq m1 month) | 1705 (memq m1 month) |
1706 (= m1 month))) | 1706 (= m1 month))) |
1707 (let ((d (or day (if (> n 0) | 1707 (let ((d (or day (if (> n 0) |
1708 1 | 1708 1 |
1709 (calendar-last-day-of-month m1 y1))))) | 1709 (calendar-last-day-of-month m1 y1))))) |
1710 (and (<= d1 d) (<= d d2)))) | 1710 (and (<= d1 d) (<= d d2)))) |
1711 ;; Only possible base dates straddle two months. | 1711 ;; Only possible base dates straddle two months. |
1712 (and (or (< y1 y2) | 1712 (and (or (< y1 y2) |
1713 (and (= y1 y2) (< m1 m2))) | 1713 (and (= y1 y2) (< m1 m2))) |
1714 (or | 1714 (or |
1715 ;; m1, d1 works as a base date. | 1715 ;; m1, d1 works as a base date. |
1716 (and | 1716 (and |
1717 (or (eq month t) | 1717 (or (eq month t) |
1718 (if (listp month) | 1718 (if (listp month) |
1719 (memq m1 month) | 1719 (memq m1 month) |
1720 (= m1 month))) | 1720 (= m1 month))) |
1721 (<= d1 (or day (if (> n 0) | 1721 (<= d1 (or day (if (> n 0) |
1722 1 | 1722 1 |
1723 (calendar-last-day-of-month m1 y1))))) | 1723 (calendar-last-day-of-month m1 y1))))) |
1724 ;; m2, d2 works as a base date. | 1724 ;; m2, d2 works as a base date. |
1725 (and (or (eq month t) | 1725 (and (or (eq month t) |
1726 (if (listp month) | 1726 (if (listp month) |
1727 (memq m2 month) | 1727 (memq m2 month) |
1728 (= m2 month))) | 1728 (= m2 month))) |
1729 (<= (or day (if (> n 0) | 1729 (<= (or day (if (> n 0) |
1730 1 | 1730 1 |
1731 (calendar-last-day-of-month m2 y2))) | 1731 (calendar-last-day-of-month m2 y2))) |
1732 d2))))) | 1732 d2))))) |
1733 (cons mark entry))))) | 1733 (cons mark entry))))) |
1734 | 1734 |
1735 ;; To be called from diary-sexp-entry, where DATE, ENTRY are bound. | 1735 ;; To be called from diary-sexp-entry, where DATE, ENTRY are bound. |
1736 (defun diary-anniversary (month day &optional year mark) | 1736 (defun diary-anniversary (month day &optional year mark) |
1737 "Anniversary diary entry. | 1737 "Anniversary diary entry. |
1738 Entry applies if date is the anniversary of MONTH, DAY, YEAR if | 1738 Entry applies if date is the anniversary of MONTH, DAY, YEAR if |
1816 ((and diary-entry | 1816 ((and diary-entry |
1817 (or (not marking-diary-entries) marking-diary-entry)) | 1817 (or (not marking-diary-entries) marking-diary-entry)) |
1818 diary-entry) | 1818 diary-entry) |
1819 ;; Diary entry may apply to `days' before date. | 1819 ;; Diary entry may apply to `days' before date. |
1820 ((and (integerp days) | 1820 ((and (integerp days) |
1821 (not diary-entry) ; diary entry does not apply to date | 1821 (not diary-entry) ; diary entry does not apply to date |
1822 (or (not marking-diary-entries) marking)) | 1822 (or (not marking-diary-entries) marking)) |
1823 (let ((date (calendar-gregorian-from-absolute | 1823 (let ((date (calendar-gregorian-from-absolute |
1824 (+ (calendar-absolute-from-gregorian date) days)))) | 1824 (+ (calendar-absolute-from-gregorian date) days)))) |
1825 (when (setq diary-entry (eval sexp)) ; re-evaluate with adjusted date | 1825 (when (setq diary-entry (eval sexp)) ; re-evaluate with adjusted date |
1826 ;; Discard any mark portion from diary-anniversary, etc. | 1826 ;; Discard any mark portion from diary-anniversary, etc. |
1924 (interactive "P") | 1924 (interactive "P") |
1925 (let ((calendar-date-display-form | 1925 (let ((calendar-date-display-form |
1926 (if european-calendar-style | 1926 (if european-calendar-style |
1927 '(day " " month " " year) | 1927 '(day " " month " " year) |
1928 '(month " " day " " year))) | 1928 '(month " " day " " year))) |
1929 (cursor (calendar-cursor-to-date t)) | 1929 (cursor (calendar-cursor-to-date t)) |
1930 (mark (or (car calendar-mark-ring) | 1930 (mark (or (car calendar-mark-ring) |
1931 (error "No mark set in this buffer"))) | 1931 (error "No mark set in this buffer"))) |
1932 start end) | 1932 start end) |
1933 (if (< (calendar-absolute-from-gregorian mark) | 1933 (if (< (calendar-absolute-from-gregorian mark) |
1934 (calendar-absolute-from-gregorian cursor)) | 1934 (calendar-absolute-from-gregorian cursor)) |
1935 (setq start mark | 1935 (setq start mark |
1936 end cursor) | 1936 end cursor) |
1937 (setq start cursor | 1937 (setq start cursor |
1938 end mark)) | 1938 end mark)) |
1939 (make-diary-entry | 1939 (make-diary-entry |
1940 (format "%s(diary-block %s %s)" | 1940 (format "%s(diary-block %s %s)" |
1941 sexp-diary-entry-symbol | 1941 sexp-diary-entry-symbol |
1942 (calendar-date-string start nil t) | 1942 (calendar-date-string start nil t) |
1943 (calendar-date-string end nil t)) | 1943 (calendar-date-string end nil t)) |
1944 arg))) | 1944 arg))) |
1945 | 1945 |
1946 ;;;###cal-autoload | 1946 ;;;###cal-autoload |
1947 (defun insert-cyclic-diary-entry (arg) | 1947 (defun insert-cyclic-diary-entry (arg) |
1948 "Insert a cyclic diary entry starting at the date given by point. | 1948 "Insert a cyclic diary entry starting at the date given by point. |
2063 (if (re-search-forward | 2063 (if (re-search-forward |
2064 (concat "^" (regexp-quote diary-nonmarking-symbol) | 2064 (concat "^" (regexp-quote diary-nonmarking-symbol) |
2065 "?\\(" (regexp-quote sexp-diary-entry-symbol) "\\)") | 2065 "?\\(" (regexp-quote sexp-diary-entry-symbol) "\\)") |
2066 limit t) | 2066 limit t) |
2067 (condition-case nil | 2067 (condition-case nil |
2068 (save-restriction | 2068 (save-restriction |
2069 (narrow-to-region (point-min) limit) | 2069 (narrow-to-region (point-min) limit) |
2070 (let ((start (point))) | 2070 (let ((start (point))) |
2071 (forward-sexp 1) | 2071 (forward-sexp 1) |
2072 (store-match-data (list start (point))) | 2072 (store-match-data (list start (point))) |
2073 t)) | 2073 t)) |
2074 (error t)))) | 2074 (error t)))) |
2075 | 2075 |
2076 (defun diary-font-lock-date-forms (month-array &optional symbol abbrev-array) | 2076 (defun diary-font-lock-date-forms (month-array &optional symbol abbrev-array) |
2077 "Create font-lock patterns for `diary-date-forms' using MONTH-ARRAY. | 2077 "Create font-lock patterns for `diary-date-forms' using MONTH-ARRAY. |
2078 If given, optional SYMBOL must be a prefix to entries. | 2078 If given, optional SYMBOL must be a prefix to entries. |
2079 If optional ABBREV-ARRAY is present, the abbreviations constructed | 2079 If optional ABBREV-ARRAY is present, the abbreviations constructed |
2086 (diary-name-pattern month-array abbrev-array))) | 2086 (diary-name-pattern month-array abbrev-array))) |
2087 (month "\\([0-9]+\\|\\*\\)") | 2087 (month "\\([0-9]+\\|\\*\\)") |
2088 (day "\\([0-9]+\\|\\*\\)") | 2088 (day "\\([0-9]+\\|\\*\\)") |
2089 (year "-?\\([0-9]+\\|\\*\\)")) | 2089 (year "-?\\([0-9]+\\|\\*\\)")) |
2090 (mapcar (lambda (x) | 2090 (mapcar (lambda (x) |
2091 (cons | 2091 (cons |
2092 (concat "^" (regexp-quote diary-nonmarking-symbol) "?" | 2092 (concat "^" (regexp-quote diary-nonmarking-symbol) "?" |
2093 (if symbol (regexp-quote symbol) "") "\\(" | 2093 (if symbol (regexp-quote symbol) "") "\\(" |
2094 (mapconcat 'eval | 2094 (mapconcat 'eval |
2095 ;; If backup, omit first item (backup) | 2095 ;; If backup, omit first item (backup) |
2096 ;; and last item (not part of date). | 2096 ;; and last item (not part of date). |
2097 (if (equal (car x) 'backup) | 2097 (if (equal (car x) 'backup) |
2098 (nreverse (cdr (reverse (cdr x)))) | 2098 (nreverse (cdr (reverse (cdr x)))) |
2099 x) | 2099 x) |
2100 "") | 2100 "") |
2101 ;; With backup, last item is not part of date. | 2101 ;; With backup, last item is not part of date. |
2102 (if (equal (car x) 'backup) | 2102 (if (equal (car x) 'backup) |
2103 (concat "\\)" (eval (car (reverse x)))) | 2103 (concat "\\)" (eval (car (reverse x)))) |
2104 "\\)")) | 2104 "\\)")) |
2105 '(1 diary-face))) | 2105 '(1 diary-face))) |
2106 diary-date-forms))) | 2106 diary-date-forms))) |
2107 | 2107 |
2108 (defvar calendar-hebrew-month-name-array-leap-year) | 2108 (defvar calendar-hebrew-month-name-array-leap-year) |
2109 (defvar calendar-islamic-month-name-array) | 2109 (defvar calendar-islamic-month-name-array) |
2110 (defvar calendar-bahai-month-name-array) | 2110 (defvar calendar-bahai-month-name-array) |
2128 nongregorian-diary-listing-hook)) | 2128 nongregorian-diary-listing-hook)) |
2129 (require 'cal-islam) | 2129 (require 'cal-islam) |
2130 (diary-font-lock-date-forms | 2130 (diary-font-lock-date-forms |
2131 calendar-islamic-month-name-array islamic-diary-entry-symbol)) | 2131 calendar-islamic-month-name-array islamic-diary-entry-symbol)) |
2132 (when (or (memq 'diary-bahai-mark-entries | 2132 (when (or (memq 'diary-bahai-mark-entries |
2133 nongregorian-diary-marking-hook) | 2133 nongregorian-diary-marking-hook) |
2134 (memq 'diary-bahai-list-entries | 2134 (memq 'diary-bahai-list-entries |
2135 nongregorian-diary-marking-hook)) | 2135 nongregorian-diary-marking-hook)) |
2136 (require 'cal-bahai) | 2136 (require 'cal-bahai) |
2137 (diary-font-lock-date-forms | 2137 (diary-font-lock-date-forms |
2138 calendar-bahai-month-name-array bahai-diary-entry-symbol)) | 2138 calendar-bahai-month-name-array bahai-diary-entry-symbol)) |
2139 (list | 2139 (list |
2140 (cons | 2140 (cons |
2141 (format "^%s.*$" (regexp-quote diary-include-string)) | 2141 (format "^%s.*$" (regexp-quote diary-include-string)) |
2142 'font-lock-keyword-face) | 2142 'font-lock-keyword-face) |
2143 (cons | 2143 (cons |
2144 (format "^%s?\\(%s\\)" (regexp-quote diary-nonmarking-symbol) | 2144 (format "^%s?\\(%s\\)" (regexp-quote diary-nonmarking-symbol) |
2145 (regexp-quote sexp-diary-entry-symbol)) | 2145 (regexp-quote sexp-diary-entry-symbol)) |
2146 '(1 font-lock-reference-face)) | 2146 '(1 font-lock-reference-face)) |
2147 (cons | 2147 (cons |
2148 (format "^%s" (regexp-quote diary-nonmarking-symbol)) | 2148 (format "^%s" (regexp-quote diary-nonmarking-symbol)) |
2149 'font-lock-reference-face) | 2149 'font-lock-reference-face) |
2150 (cons | 2150 (cons |
2151 (format "^%s?%s" (regexp-quote diary-nonmarking-symbol) | 2151 (format "^%s?%s" (regexp-quote diary-nonmarking-symbol) |
2152 (regexp-opt (mapcar 'regexp-quote | 2152 (regexp-opt (mapcar 'regexp-quote |
2153 (list hebrew-diary-entry-symbol | 2153 (list hebrew-diary-entry-symbol |
2154 islamic-diary-entry-symbol | 2154 islamic-diary-entry-symbol |
2155 bahai-diary-entry-symbol)) | 2155 bahai-diary-entry-symbol)) |
2156 t)) | 2156 t)) |
2157 '(1 font-lock-reference-face)) | 2157 '(1 font-lock-reference-face)) |
2158 '(diary-font-lock-sexps . font-lock-keyword-face) | 2158 '(diary-font-lock-sexps . font-lock-keyword-face) |
2159 `(,(format "\\(^\\|\\s-\\)%s\\(-%s\\)?" diary-time-regexp | 2159 `(,(format "\\(^\\|\\s-\\)%s\\(-%s\\)?" diary-time-regexp |
2160 diary-time-regexp) | 2160 diary-time-regexp) |
2161 . 'diary-time)))) | 2161 . 'diary-time)))) |
2162 | 2162 |
2163 (defvar diary-font-lock-keywords (diary-font-lock-keywords) | 2163 (defvar diary-font-lock-keywords (diary-font-lock-keywords) |
2164 "Forms to highlight in `diary-mode'.") | 2164 "Forms to highlight in `diary-mode'.") |
2165 | 2165 |
2182 Arg TEST-ONLY non-nil means return non-nil if and only if the | 2182 Arg TEST-ONLY non-nil means return non-nil if and only if the |
2183 message contains an appointment, don't make a diary entry." | 2183 message contains an appointment, don't make a diary entry." |
2184 (catch 'finished | 2184 (catch 'finished |
2185 (let (format-string) | 2185 (let (format-string) |
2186 (dotimes (i (length diary-outlook-formats)) | 2186 (dotimes (i (length diary-outlook-formats)) |
2187 (when (eq 0 (string-match (car (nth i diary-outlook-formats)) | 2187 (when (eq 0 (string-match (car (nth i diary-outlook-formats)) |
2188 body)) | 2188 body)) |
2189 (unless test-only | 2189 (unless test-only |
2190 (setq format-string (cdr (nth i diary-outlook-formats))) | 2190 (setq format-string (cdr (nth i diary-outlook-formats))) |
2191 (save-excursion | 2191 (save-excursion |
2192 (save-window-excursion | 2192 (save-window-excursion |
2193 ;; Fixme: References to optional fields in the format | 2193 ;; Fixme: References to optional fields in the format |
2194 ;; are treated literally, not replaced by the empty | 2194 ;; are treated literally, not replaced by the empty |
2195 ;; string. I think this is an Emacs bug. | 2195 ;; string. I think this is an Emacs bug. |
2196 (make-diary-entry | 2196 (make-diary-entry |
2197 (format (replace-match (if (functionp format-string) | 2197 (format (replace-match (if (functionp format-string) |
2198 (funcall format-string body) | 2198 (funcall format-string body) |
2199 format-string) | 2199 format-string) |
2200 t nil (match-string 0 body)) | 2200 t nil (match-string 0 body)) |
2201 subject)) | 2201 subject)) |
2202 (save-buffer)))) | 2202 (save-buffer)))) |
2203 (throw 'finished t)))) | 2203 (throw 'finished t)))) |
2204 nil)) | 2204 nil)) |
2205 | 2205 |
2206 (defun diary-from-outlook (&optional noconfirm) | 2206 (defun diary-from-outlook (&optional noconfirm) |
2207 "Maybe snarf diary entry from current Outlook-generated message. | 2207 "Maybe snarf diary entry from current Outlook-generated message. |
2208 Currently knows about Gnus and Rmail modes. Unless the optional | 2208 Currently knows about Gnus and Rmail modes. Unless the optional |
2209 argument NOCONFIRM is non-nil (which is the case when this | 2209 argument NOCONFIRM is non-nil (which is the case when this |
2210 function is called interactively), then if an entry is found the | 2210 function is called interactively), then if an entry is found the |
2211 user is asked to confirm its addition." | 2211 user is asked to confirm its addition." |
2212 (interactive "p") | 2212 (interactive "p") |
2213 (let ((func (cond | 2213 (let ((func (cond |
2214 ((eq major-mode 'rmail-mode) | 2214 ((eq major-mode 'rmail-mode) |
2215 #'diary-from-outlook-rmail) | 2215 #'diary-from-outlook-rmail) |
2216 ((memq major-mode '(gnus-summary-mode gnus-article-mode)) | 2216 ((memq major-mode '(gnus-summary-mode gnus-article-mode)) |
2217 #'diary-from-outlook-gnus) | 2217 #'diary-from-outlook-gnus) |
2218 (t (error "Don't know how to snarf in `%s'" major-mode))))) | 2218 (t (error "Don't know how to snarf in `%s'" major-mode))))) |
2219 (funcall func noconfirm))) | 2219 (funcall func noconfirm))) |
2220 | 2220 |
2221 | 2221 |
2222 (defvar gnus-article-mime-handles) | 2222 (defvar gnus-article-mime-handles) |
2223 (defvar gnus-article-buffer) | 2223 (defvar gnus-article-buffer) |
2234 Add this function to `gnus-article-prepare-hook' to notice appointments | 2234 Add this function to `gnus-article-prepare-hook' to notice appointments |
2235 automatically." | 2235 automatically." |
2236 (interactive "p") | 2236 (interactive "p") |
2237 (with-current-buffer gnus-article-buffer | 2237 (with-current-buffer gnus-article-buffer |
2238 (let ((subject (gnus-fetch-field "subject")) | 2238 (let ((subject (gnus-fetch-field "subject")) |
2239 (body (if gnus-article-mime-handles | 2239 (body (if gnus-article-mime-handles |
2240 ;; We're multipart. Don't get confused by part | 2240 ;; We're multipart. Don't get confused by part |
2241 ;; buttons &c. Assume info is in first part. | 2241 ;; buttons &c. Assume info is in first part. |
2242 (mm-get-part (nth 1 gnus-article-mime-handles)) | 2242 (mm-get-part (nth 1 gnus-article-mime-handles)) |
2243 (save-restriction | 2243 (save-restriction |
2244 (gnus-narrow-to-body) | 2244 (gnus-narrow-to-body) |
2245 (buffer-string))))) | 2245 (buffer-string))))) |
2246 (when (diary-from-outlook-internal t) | 2246 (when (diary-from-outlook-internal t) |
2247 (when (or noconfirm (y-or-n-p "Snarf diary entry? ")) | 2247 (when (or noconfirm (y-or-n-p "Snarf diary entry? ")) |
2248 (diary-from-outlook-internal) | 2248 (diary-from-outlook-internal) |
2249 (message "Diary entry added")))))) | 2249 (message "Diary entry added")))))) |
2250 | 2250 |
2251 (custom-add-option 'gnus-article-prepare-hook 'diary-from-outlook-gnus) | 2251 (custom-add-option 'gnus-article-prepare-hook 'diary-from-outlook-gnus) |
2252 | 2252 |
2253 | 2253 |
2254 (defvar rmail-buffer) | 2254 (defvar rmail-buffer) |
2259 this function is called interactively), then if an entry is found the | 2259 this function is called interactively), then if an entry is found the |
2260 user is asked to confirm its addition." | 2260 user is asked to confirm its addition." |
2261 (interactive "p") | 2261 (interactive "p") |
2262 (with-current-buffer rmail-buffer | 2262 (with-current-buffer rmail-buffer |
2263 (let ((subject (mail-fetch-field "subject")) | 2263 (let ((subject (mail-fetch-field "subject")) |
2264 (body (buffer-substring (save-excursion | 2264 (body (buffer-substring (save-excursion |
2265 (rfc822-goto-eoh) | 2265 (rfc822-goto-eoh) |
2266 (point)) | 2266 (point)) |
2267 (point-max)))) | 2267 (point-max)))) |
2268 (when (diary-from-outlook-internal t) | 2268 (when (diary-from-outlook-internal t) |
2269 (when (or noconfirm (y-or-n-p "Snarf diary entry? ")) | 2269 (when (or noconfirm (y-or-n-p "Snarf diary entry? ")) |
2270 (diary-from-outlook-internal) | 2270 (diary-from-outlook-internal) |
2271 (message "Diary entry added")))))) | 2271 (message "Diary entry added")))))) |
2272 | 2272 |
2273 | 2273 |
2274 (provide 'diary-lib) | 2274 (provide 'diary-lib) |
2275 | 2275 |
2276 ;; arch-tag: 22dd506e-2e33-410d-9ae1-095a0c1b2010 | 2276 ;; arch-tag: 22dd506e-2e33-410d-9ae1-095a0c1b2010 |