mhc 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +27 -0
- data/.rspec +2 -0
- data/.travis.yml +3 -0
- data/COPYRIGHT +28 -0
- data/Gemfile +8 -0
- data/README.org +209 -0
- data/Rakefile +13 -0
- data/bin/mhc +312 -0
- data/emacs/Cask +25 -0
- data/emacs/Makefile +58 -0
- data/emacs/mhc-calendar.el +1723 -0
- data/emacs/mhc-calfw.el +135 -0
- data/emacs/mhc-compat.el +90 -0
- data/emacs/mhc-date.el +642 -0
- data/emacs/mhc-day.el +149 -0
- data/emacs/mhc-db.el +158 -0
- data/emacs/mhc-draft.el +211 -0
- data/emacs/mhc-e21.el +167 -0
- data/emacs/mhc-face.el +236 -0
- data/emacs/mhc-file.el +224 -0
- data/emacs/mhc-guess.el +648 -0
- data/emacs/mhc-header.el +176 -0
- data/emacs/mhc-logic.el +563 -0
- data/emacs/mhc-message.el +130 -0
- data/emacs/mhc-minibuf.el +466 -0
- data/emacs/mhc-misc.el +248 -0
- data/emacs/mhc-mua.el +260 -0
- data/emacs/mhc-parse.el +286 -0
- data/emacs/mhc-process.el +35 -0
- data/emacs/mhc-ps.el +1174 -0
- data/emacs/mhc-record.el +201 -0
- data/emacs/mhc-schedule.el +202 -0
- data/emacs/mhc-summary.el +763 -0
- data/emacs/mhc-sync.el +158 -0
- data/emacs/mhc-vars.el +149 -0
- data/emacs/mhc.el +1114 -0
- data/icons/Anniversary.xbm +6 -0
- data/icons/Anniversary.xpm +27 -0
- data/icons/Birthday.xbm +6 -0
- data/icons/Birthday.xpm +25 -0
- data/icons/Business.xbm +6 -0
- data/icons/Business.xpm +24 -0
- data/icons/CheckBox.xbm +6 -0
- data/icons/CheckBox.xpm +24 -0
- data/icons/CheckedBox.xbm +6 -0
- data/icons/CheckedBox.xpm +25 -0
- data/icons/Conflict.xbm +6 -0
- data/icons/Conflict.xpm +22 -0
- data/icons/Date.xbm +6 -0
- data/icons/Date.xpm +29 -0
- data/icons/Holiday.xbm +6 -0
- data/icons/Holiday.xpm +25 -0
- data/icons/Link.xbm +6 -0
- data/icons/Link.xpm +25 -0
- data/icons/Other.xbm +6 -0
- data/icons/Other.xpm +28 -0
- data/icons/Party.xbm +6 -0
- data/icons/Party.xpm +23 -0
- data/icons/Private.xbm +6 -0
- data/icons/Private.xpm +26 -0
- data/icons/Recurrence.xbm +6 -0
- data/icons/Recurrence.xpm +98 -0
- data/icons/Vacation.xbm +6 -0
- data/icons/Vacation.xpm +26 -0
- data/lib/mhc.rb +45 -0
- data/lib/mhc/builder.rb +64 -0
- data/lib/mhc/caldav.rb +304 -0
- data/lib/mhc/calendar.rb +106 -0
- data/lib/mhc/command.rb +13 -0
- data/lib/mhc/command/cache.rb +14 -0
- data/lib/mhc/command/completions.rb +108 -0
- data/lib/mhc/command/init.rb +133 -0
- data/lib/mhc/command/scan.rb +33 -0
- data/lib/mhc/command/sync.rb +22 -0
- data/lib/mhc/config.rb +229 -0
- data/lib/mhc/converter.rb +330 -0
- data/lib/mhc/datastore.rb +164 -0
- data/lib/mhc/date_enumerator.rb +274 -0
- data/lib/mhc/date_frame.rb +124 -0
- data/lib/mhc/date_helper.rb +49 -0
- data/lib/mhc/etag.rb +68 -0
- data/lib/mhc/event.rb +396 -0
- data/lib/mhc/formatter.rb +312 -0
- data/lib/mhc/logger.rb +94 -0
- data/lib/mhc/modifier.rb +149 -0
- data/lib/mhc/occurrence.rb +94 -0
- data/lib/mhc/occurrence_enumerator.rb +113 -0
- data/lib/mhc/property_value.rb +33 -0
- data/lib/mhc/property_value/date.rb +190 -0
- data/lib/mhc/property_value/integer.rb +15 -0
- data/lib/mhc/property_value/list.rb +41 -0
- data/lib/mhc/property_value/period.rb +49 -0
- data/lib/mhc/property_value/range.rb +100 -0
- data/lib/mhc/property_value/recurrence_condition.rb +272 -0
- data/lib/mhc/property_value/text.rb +11 -0
- data/lib/mhc/property_value/time.rb +45 -0
- data/lib/mhc/query.rb +210 -0
- data/lib/mhc/sync.rb +46 -0
- data/lib/mhc/sync/driver.rb +108 -0
- data/lib/mhc/sync/status.rb +70 -0
- data/lib/mhc/sync/status_manager.rb +142 -0
- data/lib/mhc/sync/strategy.rb +233 -0
- data/lib/mhc/sync/syncinfo.rb +98 -0
- data/lib/mhc/templates/config.yml.erb +142 -0
- data/lib/mhc/version.rb +4 -0
- data/lib/mhc/webdav.rb +319 -0
- data/mhc.gemspec +24 -0
- data/samples/DOT.mhc-config.yml +116 -0
- data/samples/japanese-holidays.mhcc +153 -0
- data/samples/mhc-completions.zsh +11 -0
- data/spec/mhc_spec.rb +682 -0
- data/spec/spec_helper.rb +9 -0
- data/xpm/close.xpm +18 -0
- data/xpm/delete.xpm +19 -0
- data/xpm/exit.xpm +18 -0
- data/xpm/month.xpm +18 -0
- data/xpm/next.xpm +18 -0
- data/xpm/next2.xpm +18 -0
- data/xpm/next_year.xpm +18 -0
- data/xpm/open.xpm +19 -0
- data/xpm/prev.xpm +18 -0
- data/xpm/prev2.xpm +18 -0
- data/xpm/prev_year.xpm +18 -0
- data/xpm/save.xpm +19 -0
- data/xpm/today.xpm +18 -0
- metadata +214 -0
data/emacs/mhc-record.el
ADDED
@@ -0,0 +1,201 @@
|
|
1
|
+
;;; -*- mode: Emacs-Lisp; coding: utf-8 -*-
|
2
|
+
|
3
|
+
;; Author: Yoshinari Nomura <nom@quickhack.net>,
|
4
|
+
;; TSUCHIYA Masatoshi <tsuchiya@namazu.org>
|
5
|
+
;; Created: 2000/05/15
|
6
|
+
;; Revised: $Date$
|
7
|
+
|
8
|
+
|
9
|
+
;;; Commentary:
|
10
|
+
|
11
|
+
;; This file is a part of MHC, and includes functions manipulate
|
12
|
+
;; MHC-RECORD structure.
|
13
|
+
|
14
|
+
|
15
|
+
;;; About MHC-RECORD structure:
|
16
|
+
|
17
|
+
;; Each MHC-RECORD structure is a cons cell has a construction as
|
18
|
+
;; follows:
|
19
|
+
;;
|
20
|
+
;; MHC-RECORD ::= ( KEY . VALUE )
|
21
|
+
;; KEY ::= string ( represents file name of record )
|
22
|
+
;; VALUE ::= [ ID SCHEDULES SEXP ]
|
23
|
+
;; ID ::= string ( represents unique id of recort )
|
24
|
+
;; SCHEDULES ::= MHC-SCHEDULE*
|
25
|
+
;; SEXP ::= S expression to get schedule.
|
26
|
+
|
27
|
+
|
28
|
+
;;; Code:
|
29
|
+
|
30
|
+
(require 'mhc-summary)
|
31
|
+
(require 'mhc-file)
|
32
|
+
(require 'mhc-draft)
|
33
|
+
(require 'mhc-logic)
|
34
|
+
|
35
|
+
(eval-when-compile
|
36
|
+
(mhc-file-setup))
|
37
|
+
|
38
|
+
;; Global Variable:
|
39
|
+
|
40
|
+
(defcustom mhc-record-log-file
|
41
|
+
"mhc-db.log"
|
42
|
+
"*Log file of DB transaction."
|
43
|
+
:group 'mhc
|
44
|
+
:type 'file)
|
45
|
+
|
46
|
+
;; Internal Variable:
|
47
|
+
|
48
|
+
(defvar mhc-record/id-counter 0)
|
49
|
+
|
50
|
+
|
51
|
+
;; Functions:
|
52
|
+
|
53
|
+
(require 'org-id)
|
54
|
+
|
55
|
+
(defun mhc-record-create-id ()
|
56
|
+
"Return unique ID string."
|
57
|
+
(org-id-new))
|
58
|
+
|
59
|
+
(defun mhc-record-new (name &optional id schedules sexp)
|
60
|
+
"Constructer of MHC-RECORD structure."
|
61
|
+
(cons name
|
62
|
+
(vector id
|
63
|
+
schedules
|
64
|
+
sexp)))
|
65
|
+
|
66
|
+
(defmacro mhc-record/key (record)
|
67
|
+
`(car ,record))
|
68
|
+
(defmacro mhc-record/value (record)
|
69
|
+
`(cdr ,record))
|
70
|
+
|
71
|
+
(defmacro mhc-record-name (record)
|
72
|
+
`(mhc-record/key ,record))
|
73
|
+
(defmacro mhc-record-id (record)
|
74
|
+
`(aref (mhc-record/value ,record) 0))
|
75
|
+
(defmacro mhc-record-schedules (record)
|
76
|
+
`(aref (mhc-record/value ,record) 1))
|
77
|
+
(defmacro mhc-record-sexp (record)
|
78
|
+
`(aref (mhc-record/value ,record) 2))
|
79
|
+
|
80
|
+
(defmacro mhc-record-set-name (record name)
|
81
|
+
`(setcar ,record ,name))
|
82
|
+
(defmacro mhc-record-set-id (record id)
|
83
|
+
`(aset (mhc-record/value ,record) 0 ,id))
|
84
|
+
(defmacro mhc-record-set-schedules (record schedules)
|
85
|
+
`(aset (mhc-record/value ,record) 1 ,schedules))
|
86
|
+
(defmacro mhc-record-set-sexp (record sexp)
|
87
|
+
`(aset (mhc-record/value ,record) 2 ,sexp))
|
88
|
+
|
89
|
+
(defun mhc-record-copy (record)
|
90
|
+
(cons (copy-sequence (mhc-record/key record))
|
91
|
+
(copy-sequence (mhc-record/value record))))
|
92
|
+
|
93
|
+
(defun mhc-record-subject (record)
|
94
|
+
(catch 'found
|
95
|
+
(let ((schedules (mhc-record-schedules record)))
|
96
|
+
(while schedules
|
97
|
+
(if (mhc-schedule-subject (car schedules))
|
98
|
+
(throw 'found (mhc-schedule-subject (car schedules))))
|
99
|
+
(setq schedules (cdr schedules))))))
|
100
|
+
|
101
|
+
(defun mhc-record-subject-as-string (record)
|
102
|
+
(or (mhc-record-subject record)
|
103
|
+
"(none)"))
|
104
|
+
|
105
|
+
(defun mhc-record-occur-multiple-p (record)
|
106
|
+
"Return t if RECORD occurs multiple times."
|
107
|
+
(let ((schedules (mhc-record-schedules record)))
|
108
|
+
(or (> (length schedules) 1)
|
109
|
+
(mhc-logic-occur-multiple-p (mhc-schedule-condition (car schedules))))))
|
110
|
+
|
111
|
+
(defun mhc-record-write-buffer (record buffer &optional old-record)
|
112
|
+
"Write BUFFER to RECORD."
|
113
|
+
(let ((modify (file-exists-p (mhc-record-name record))))
|
114
|
+
(with-current-buffer buffer
|
115
|
+
(mhc-draft-increment-sequence)
|
116
|
+
(mhc-draft-translate)
|
117
|
+
(mhc-file-make-directory
|
118
|
+
(file-name-directory (mhc-record-name record)))
|
119
|
+
(mhc-write-region-as-coding-system mhc-default-coding-system
|
120
|
+
(point-min)
|
121
|
+
(point-max)
|
122
|
+
(mhc-record-name record)
|
123
|
+
nil 'nomsg)
|
124
|
+
(set-buffer-modified-p nil)
|
125
|
+
(if modify
|
126
|
+
(prog1
|
127
|
+
(mhc-file-modify (mhc-record-name record))
|
128
|
+
(mhc-record/append-log record 'modify))
|
129
|
+
(if old-record
|
130
|
+
(prog2
|
131
|
+
(mhc-file-remove (mhc-record-name old-record))
|
132
|
+
(mhc-file-add (mhc-record-name record))
|
133
|
+
(mhc-record/append-log record 'modify))
|
134
|
+
(prog1
|
135
|
+
(mhc-file-add (mhc-record-name record))
|
136
|
+
(mhc-record/append-log record 'add)))))))
|
137
|
+
|
138
|
+
(defun mhc-record-delete (record)
|
139
|
+
(prog1 (mhc-file-remove (mhc-record-name record))
|
140
|
+
(mhc-record/append-log record 'delete)))
|
141
|
+
|
142
|
+
(defun mhc-record/append-log (record status)
|
143
|
+
(if mhc-record-log-file
|
144
|
+
(let ((tmp-buffer (mhc-get-buffer-create " *mhc-record-append-log*")))
|
145
|
+
(with-current-buffer tmp-buffer
|
146
|
+
(delete-region (point-min) (point-max))
|
147
|
+
(insert (format "%c %s %s %s %s\n"
|
148
|
+
(cond
|
149
|
+
((eq status 'add) ?A)
|
150
|
+
((eq status 'delete) ?D)
|
151
|
+
((eq status 'modify) ?M)
|
152
|
+
(t ??))
|
153
|
+
(format-time-string "%Y-%m-%d %T")
|
154
|
+
(mhc-record-id record)
|
155
|
+
(mhc-record-name record)
|
156
|
+
(mhc-record-subject-as-string record)))
|
157
|
+
(mhc-write-region-as-coding-system mhc-default-coding-system
|
158
|
+
(point-min)
|
159
|
+
(point-max)
|
160
|
+
(expand-file-name
|
161
|
+
mhc-record-log-file
|
162
|
+
(expand-file-name "status/log" (mhc-config-base-directory)))
|
163
|
+
'append
|
164
|
+
'nomsg)))))
|
165
|
+
|
166
|
+
|
167
|
+
|
168
|
+
(provide 'mhc-record)
|
169
|
+
|
170
|
+
;;; Copyright Notice:
|
171
|
+
|
172
|
+
;; Copyright (C) 1999, 2000 Yoshinari Nomura. All rights reserved.
|
173
|
+
;; Copyright (C) 2000 MHC developing team. All rights reserved.
|
174
|
+
|
175
|
+
;; Redistribution and use in source and binary forms, with or without
|
176
|
+
;; modification, are permitted provided that the following conditions
|
177
|
+
;; are met:
|
178
|
+
;;
|
179
|
+
;; 1. Redistributions of source code must retain the above copyright
|
180
|
+
;; notice, this list of conditions and the following disclaimer.
|
181
|
+
;; 2. Redistributions in binary form must reproduce the above copyright
|
182
|
+
;; notice, this list of conditions and the following disclaimer in the
|
183
|
+
;; documentation and/or other materials provided with the distribution.
|
184
|
+
;; 3. Neither the name of the team nor the names of its contributors
|
185
|
+
;; may be used to endorse or promote products derived from this software
|
186
|
+
;; without specific prior written permission.
|
187
|
+
;;
|
188
|
+
;; THIS SOFTWARE IS PROVIDED BY THE TEAM AND CONTRIBUTORS ``AS IS''
|
189
|
+
;; AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
190
|
+
;; LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
|
191
|
+
;; FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
|
192
|
+
;; THE TEAM OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
193
|
+
;; INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
194
|
+
;; (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
195
|
+
;; SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
196
|
+
;; HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
197
|
+
;; STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
198
|
+
;; ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
|
199
|
+
;; OF THE POSSIBILITY OF SUCH DAMAGE.
|
200
|
+
|
201
|
+
;;; mhc-record.el ends here
|
@@ -0,0 +1,202 @@
|
|
1
|
+
;;; -*- mode: Emacs-Lisp; coding: utf-8 -*-
|
2
|
+
|
3
|
+
;; Author: Yoshinari Nomura <nom@quickhack.net>,
|
4
|
+
;; TSUCHIYA Masatoshi <tsuchiya@namazu.org>
|
5
|
+
;; Created: 1997/10/12
|
6
|
+
;; Revised: $Date: 2004/05/06 16:35:12 $
|
7
|
+
|
8
|
+
|
9
|
+
;;; Commentary:
|
10
|
+
|
11
|
+
;; This file is a part of MHC, and includes functions to manipulate
|
12
|
+
;; MHC-SCHEDULE structure.
|
13
|
+
|
14
|
+
|
15
|
+
;; About MHC-SCHEDULE structure:
|
16
|
+
|
17
|
+
;; Each MHC-SCHEDULE structure is a vector has a construction as
|
18
|
+
;; follows:
|
19
|
+
;;
|
20
|
+
;; MHC-SCHEDULE ::= [ RECORD CONDITION SUBJECT LOCATION TIME ALARM CATEGORIES PRIORITY REGION RECURRENCE-TAG SEQUENCE]
|
21
|
+
;; RECORD ::= MHC-RECORD
|
22
|
+
;; CONDITION ::= MHC-LOGIC
|
23
|
+
;; SUBJECT ::= string ( represents subject of schedule )
|
24
|
+
;; LOCATION ::= string ( represents location of schedule )
|
25
|
+
;; TIME ::= integer ( represents minutes of day from midnight )
|
26
|
+
;; ALARM ::= string
|
27
|
+
;; CATEGORIES ::= CATEGORY*
|
28
|
+
;; CATEGORY ::= string ( represents category of schedule )
|
29
|
+
;; PRIORITY ::= integer
|
30
|
+
;; REGION ::= ( START . END )
|
31
|
+
;; START ::= integer ( represents start point of headers of schedule )
|
32
|
+
;; END ::= integer ( represents end point of headers of schedule )
|
33
|
+
;; RECURRENCE-TAG ::= string
|
34
|
+
;; SEQUENCE ::= integer
|
35
|
+
|
36
|
+
|
37
|
+
;;; Codes:
|
38
|
+
(defun mhc-schedule-new
|
39
|
+
(record &optional condition subject location time alarm categories priority region recurrence-tag sequence)
|
40
|
+
"Constructor of MHC-SCHEDULE structure."
|
41
|
+
(let ((new (vector record
|
42
|
+
(or condition (mhc-logic-new))
|
43
|
+
subject
|
44
|
+
location
|
45
|
+
time
|
46
|
+
alarm
|
47
|
+
categories
|
48
|
+
priority
|
49
|
+
(or region (cons nil nil))
|
50
|
+
recurrence-tag
|
51
|
+
sequence)))
|
52
|
+
(mhc-record-set-schedules record (cons new (mhc-record-schedules record)))
|
53
|
+
new))
|
54
|
+
|
55
|
+
(defsubst mhc-schedule-record (schedule)
|
56
|
+
(if schedule (aref schedule 0)))
|
57
|
+
(defsubst mhc-schedule-condition (schedule)
|
58
|
+
(if schedule (aref schedule 1)))
|
59
|
+
(defsubst mhc-schedule-subject (schedule)
|
60
|
+
(if schedule (aref schedule 2)))
|
61
|
+
(defsubst mhc-schedule-location (schedule)
|
62
|
+
(if schedule (aref schedule 3)))
|
63
|
+
(defsubst mhc-schedule-time (schedule)
|
64
|
+
(if schedule (aref schedule 4)))
|
65
|
+
(defsubst mhc-schedule-alarm (schedule)
|
66
|
+
(if schedule (aref schedule 5)))
|
67
|
+
(defsubst mhc-schedule-categories (schedule)
|
68
|
+
(if schedule (aref schedule 6)))
|
69
|
+
(defsubst mhc-schedule-priority (schedule)
|
70
|
+
(if schedule (aref schedule 7)))
|
71
|
+
(defsubst mhc-schedule-region (schedule)
|
72
|
+
(if schedule (aref schedule 8)))
|
73
|
+
(defsubst mhc-schedule-recurrence-tag (schedule)
|
74
|
+
(if schedule (aref schedule 9)))
|
75
|
+
(defsubst mhc-schedule-sequence (schedule)
|
76
|
+
(if schedule (aref schedule 10)))
|
77
|
+
|
78
|
+
(defmacro mhc-schedule-time-begin (schedule)
|
79
|
+
`(car (mhc-schedule-time ,schedule)))
|
80
|
+
(defmacro mhc-schedule-time-end (schedule)
|
81
|
+
`(cdr (mhc-schedule-time ,schedule)))
|
82
|
+
(defmacro mhc-schedule-region-start (schedule)
|
83
|
+
`(car (mhc-schedule-region ,schedule)))
|
84
|
+
(defmacro mhc-schedule-region-end (schedule)
|
85
|
+
`(cdr (mhc-schedule-region ,schedule)))
|
86
|
+
|
87
|
+
(defmacro mhc-schedule/set-subject (schedule subject)
|
88
|
+
`(aset ,schedule 2 ,subject))
|
89
|
+
(defmacro mhc-schedule/set-location (schedule location)
|
90
|
+
`(aset ,schedule 3 ,location))
|
91
|
+
(defmacro mhc-schedule/set-time (schedule begin end)
|
92
|
+
`(aset ,schedule 4 (cons ,begin ,end)))
|
93
|
+
(defmacro mhc-schedule/set-alarm (schedule alarm)
|
94
|
+
`(aset ,schedule 5 ,alarm))
|
95
|
+
(defmacro mhc-schedule/set-categories (schedule categories)
|
96
|
+
`(aset ,schedule 6 ,categories))
|
97
|
+
(defmacro mhc-schedule/set-priority (schedule priority)
|
98
|
+
`(aset ,schedule 7 ,priority))
|
99
|
+
(defmacro mhc-schedule/set-region-start (schedule start)
|
100
|
+
`(setcar (aref ,schedule 8) ,start))
|
101
|
+
(defmacro mhc-schedule/set-region-end (schedule end)
|
102
|
+
`(setcdr (aref ,schedule 8) ,end))
|
103
|
+
(defmacro mhc-schedule/set-recurrence-tag (schedule tag)
|
104
|
+
`(aset ,schedule 9 ,tag))
|
105
|
+
(defmacro mhc-schedule/set-sequence (schedule sequence)
|
106
|
+
`(aset ,schedule 10 ,sequence))
|
107
|
+
|
108
|
+
(defun mhc-schedule-append-default (schedule default)
|
109
|
+
(or (mhc-schedule-subject schedule)
|
110
|
+
(mhc-schedule/set-subject schedule (mhc-schedule-subject default)))
|
111
|
+
(or (mhc-schedule-location schedule)
|
112
|
+
(mhc-schedule/set-location schedule (mhc-schedule-location default)))
|
113
|
+
(or (mhc-schedule-time schedule)
|
114
|
+
(not (mhc-schedule-time default))
|
115
|
+
(mhc-schedule/set-time schedule
|
116
|
+
(mhc-schedule-time-begin default)
|
117
|
+
(mhc-schedule-time-end default)))
|
118
|
+
(or (mhc-schedule-alarm schedule)
|
119
|
+
(mhc-schedule/set-alarm schedule (mhc-schedule-alarm default)))
|
120
|
+
(or (mhc-schedule-categories schedule)
|
121
|
+
(mhc-schedule/set-categories schedule (mhc-schedule-categories default)))
|
122
|
+
(or (mhc-schedule-recurrence-tag schedule)
|
123
|
+
(mhc-schedule/set-recurrence-tag schedule (mhc-schedule-recurrence-tag default))))
|
124
|
+
|
125
|
+
|
126
|
+
(defsubst mhc-schedule/time-to-string (minutes)
|
127
|
+
(format "%02d:%02d" (/ minutes 60) (% minutes 60)))
|
128
|
+
|
129
|
+
|
130
|
+
(defun mhc-schedule-time-as-string (schedule)
|
131
|
+
(let ((time (mhc-schedule-time schedule)))
|
132
|
+
(cond
|
133
|
+
((and (car time) (cdr time))
|
134
|
+
(concat (mhc-schedule/time-to-string (car time))
|
135
|
+
"-"
|
136
|
+
(mhc-schedule/time-to-string (cdr time))))
|
137
|
+
((car time)
|
138
|
+
(mhc-schedule/time-to-string (car time)))
|
139
|
+
((cdr time)
|
140
|
+
(concat "-" (mhc-schedule/time-to-string (cdr time))))
|
141
|
+
(t ""))))
|
142
|
+
|
143
|
+
|
144
|
+
(defun mhc-schedule-subject-as-string (schedule)
|
145
|
+
(or (mhc-schedule-subject schedule) "(none)"))
|
146
|
+
|
147
|
+
|
148
|
+
(defun mhc-schedule-categories-as-string (schedule)
|
149
|
+
(let ((categories (mhc-schedule-categories schedule)))
|
150
|
+
(if categories
|
151
|
+
(mapconcat (function identity) categories " ")
|
152
|
+
"")))
|
153
|
+
|
154
|
+
|
155
|
+
(defun mhc-schedule-in-category-p (schedule category)
|
156
|
+
(and schedule
|
157
|
+
(if (listp category)
|
158
|
+
(catch 'found
|
159
|
+
(while category
|
160
|
+
(if (member (downcase (car category)) (mhc-schedule-categories schedule))
|
161
|
+
(throw 'found t))
|
162
|
+
(setq category (cdr category))))
|
163
|
+
(member (downcase category) (mhc-schedule-categories schedule)))))
|
164
|
+
|
165
|
+
|
166
|
+
(defun mhc-schedule-recurrence-tag-as-string (schedule)
|
167
|
+
(or (mhc-schedule-recurrence-tag schedule) ""))
|
168
|
+
|
169
|
+
(provide 'mhc-schedule)
|
170
|
+
|
171
|
+
;;; Copyright Notice:
|
172
|
+
|
173
|
+
;; Copyright (C) 1999, 2000 Yoshinari Nomura. All rights reserved.
|
174
|
+
;; Copyright (C) 2000 MHC developing team. All rights reserved.
|
175
|
+
|
176
|
+
;; Redistribution and use in source and binary forms, with or without
|
177
|
+
;; modification, are permitted provided that the following conditions
|
178
|
+
;; are met:
|
179
|
+
;;
|
180
|
+
;; 1. Redistributions of source code must retain the above copyright
|
181
|
+
;; notice, this list of conditions and the following disclaimer.
|
182
|
+
;; 2. Redistributions in binary form must reproduce the above copyright
|
183
|
+
;; notice, this list of conditions and the following disclaimer in the
|
184
|
+
;; documentation and/or other materials provided with the distribution.
|
185
|
+
;; 3. Neither the name of the team nor the names of its contributors
|
186
|
+
;; may be used to endorse or promote products derived from this software
|
187
|
+
;; without specific prior written permission.
|
188
|
+
;;
|
189
|
+
;; THIS SOFTWARE IS PROVIDED BY THE TEAM AND CONTRIBUTORS ``AS IS''
|
190
|
+
;; AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
191
|
+
;; LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
|
192
|
+
;; FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
|
193
|
+
;; THE TEAM OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
194
|
+
;; INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
195
|
+
;; (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
196
|
+
;; SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
197
|
+
;; HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
198
|
+
;; STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
199
|
+
;; ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
|
200
|
+
;; OF THE POSSIBILITY OF SUCH DAMAGE.
|
201
|
+
|
202
|
+
;;; mhc-schedule.el ends here.
|
@@ -0,0 +1,763 @@
|
|
1
|
+
;;; mhc-summary.el --- Summary major mode in MHC.
|
2
|
+
|
3
|
+
;; Author: Yoshinari Nomura <nom@quickhack.net>,
|
4
|
+
;; TSUCHIYA Masatoshi <tsuchiya@namazu.org>
|
5
|
+
;; Created: 2000/05/01
|
6
|
+
;; Revised: $Date$
|
7
|
+
|
8
|
+
|
9
|
+
;;; Commentary:
|
10
|
+
|
11
|
+
;; This file is a part of MHC.
|
12
|
+
|
13
|
+
;; This file consists of two parts: the first part contains MUA
|
14
|
+
;; backend functions, and the second part contains functions to make
|
15
|
+
;; summary contents.
|
16
|
+
|
17
|
+
|
18
|
+
;;; About MUA Backend:
|
19
|
+
|
20
|
+
;; In order to define new MUA backend, it is required to define these
|
21
|
+
;; methods.
|
22
|
+
;;
|
23
|
+
;; (mhc-foo-summary-filename)
|
24
|
+
;; Return the file name of the article on the current line in
|
25
|
+
;; this summary buffer.
|
26
|
+
;;
|
27
|
+
;; (mhc-foo-summary-display-article)
|
28
|
+
;; Display the article on the current line in this buffer.
|
29
|
+
;;
|
30
|
+
;; (mhc-foo-get-import-buffer GET-ORIGINAL)
|
31
|
+
;; Return buffer visiting import article. If GET-ORIGINAL,
|
32
|
+
;; return it without MIME decode.
|
33
|
+
;;
|
34
|
+
;; (mhc-foo-generate-summary-buffer DATE)
|
35
|
+
;; Generate summary buffer of mailer, and change current
|
36
|
+
;; buffer to it. This function will be called at the top of
|
37
|
+
;; mhc-scan-month.
|
38
|
+
;;
|
39
|
+
;; (mhc-foo-insert-summary-contents INSERTER)
|
40
|
+
;; Insert schedule with INSERTER.
|
41
|
+
;;
|
42
|
+
;; (mhc-foo-summary-mode-setup DATE)
|
43
|
+
;; Setup buffer as summary of mailer. This function will be
|
44
|
+
;; called at the end of mhc-scan-month.
|
45
|
+
;;
|
46
|
+
;; (mhc-foo-highlight-message FOR-DRAFT)
|
47
|
+
;; Hilight message in the current buffer.
|
48
|
+
;; If FOR-DRAFT is non-nil, Hilight message as draft message."
|
49
|
+
;;
|
50
|
+
;; (mhc-foo-eword-decode-string STRING)
|
51
|
+
;; Decode encoded STRING.
|
52
|
+
;;
|
53
|
+
;; (mhc-foo-decode-header)
|
54
|
+
;; Decode encoded header.
|
55
|
+
;;
|
56
|
+
;; Define these methods appropriately, and put definitions as follows:
|
57
|
+
;;
|
58
|
+
;; (provide 'mhc-foo)
|
59
|
+
;; (put 'mhc-foo 'summary-filename 'mhc-foo-summary-filename)
|
60
|
+
;; (put 'mhc-foo 'summary-display-article 'mhc-foo-summary-display-article)
|
61
|
+
;; (put 'mhc-foo 'get-import-buffer 'mhc-foo-get-import-buffer)
|
62
|
+
;; (put 'mhc-foo 'generate-summary-buffer 'mhc-foo-generate-summary-buffer)
|
63
|
+
;; (put 'mhc-foo 'insert-summary-contents 'mhc-foo-insert-summary-contents)
|
64
|
+
;; (put 'mhc-foo 'summary-mode-setup 'mhc-foo-summary-mode-setup)
|
65
|
+
;; (put 'mhc-foo 'highlight-message 'mhc-foo-highlight-message)
|
66
|
+
;; (put 'mhc-foo 'eword-decode-string 'mhc-foo-eword-decode-string)
|
67
|
+
;; (put 'mhc-foo 'decode-header 'mhc-foo-decode-header)
|
68
|
+
|
69
|
+
;;; Code:
|
70
|
+
|
71
|
+
(require 'mhc-vars)
|
72
|
+
(require 'mhc-day)
|
73
|
+
(require 'mhc-compat)
|
74
|
+
(require 'mhc-schedule)
|
75
|
+
(require 'bytecomp)
|
76
|
+
|
77
|
+
;;; Global Variables:
|
78
|
+
|
79
|
+
(defcustom mhc-summary-language 'english
|
80
|
+
"*Language of the summary."
|
81
|
+
:group 'mhc
|
82
|
+
:type '(choice (const :tag "English" english)
|
83
|
+
(const :tag "Japanese" japanese)))
|
84
|
+
|
85
|
+
(defcustom mhc-summary-use-cw nil
|
86
|
+
"*If non-nil, insert `Calendar week number' instead of `Monday'."
|
87
|
+
:group 'mhc
|
88
|
+
:type '(choice (const :tag "Use" t)
|
89
|
+
(const :tag "No" nil)))
|
90
|
+
|
91
|
+
(defcustom mhc-use-week-separator t
|
92
|
+
"*If non-nil insert separator in summary buffer."
|
93
|
+
:group 'mhc
|
94
|
+
:type 'boolean)
|
95
|
+
|
96
|
+
(defcustom mhc-summary-separator ?-
|
97
|
+
"*Character of the separator as 'mhc-use-week-separator'."
|
98
|
+
:group 'mhc
|
99
|
+
:type 'character)
|
100
|
+
|
101
|
+
(defcustom mhc-use-month-separator t
|
102
|
+
"*Insert separator in summary buffer for wide scope."
|
103
|
+
:group 'mhc
|
104
|
+
:type '(choice (const :tag "Insert (full width)" t)
|
105
|
+
(integer :tag "Insert (number of width)")
|
106
|
+
(const :tag "Not use" nil)))
|
107
|
+
|
108
|
+
(defcustom mhc-summary-month-separator ?=
|
109
|
+
"*Character of the separator as 'mhc-use-month-separator'."
|
110
|
+
:group 'mhc
|
111
|
+
:type 'character)
|
112
|
+
|
113
|
+
(defcustom mhc-summary-string-conflict "[C]"
|
114
|
+
"*String which indicates conflicts in summary buffer."
|
115
|
+
:group 'mhc
|
116
|
+
:type 'string)
|
117
|
+
|
118
|
+
(defcustom mhc-summary-string-recurrence "[R]"
|
119
|
+
"*String which indicates recurrences in summary buffer."
|
120
|
+
:group 'mhc
|
121
|
+
:type 'string)
|
122
|
+
|
123
|
+
(defcustom mhc-summary-string-secret "[SECRET]"
|
124
|
+
"*String which hides private subjects in summary buffer."
|
125
|
+
:group 'mhc
|
126
|
+
:type 'string)
|
127
|
+
|
128
|
+
(defcustom mhc-use-icon t
|
129
|
+
"*If non-nil, schedule icon is used."
|
130
|
+
:group 'mhc
|
131
|
+
:type 'boolean)
|
132
|
+
|
133
|
+
(defcustom mhc-icon-path (if (fboundp 'locate-data-directory)
|
134
|
+
(locate-data-directory "mhc"))
|
135
|
+
"*Icon path for MHC."
|
136
|
+
:group 'mhc
|
137
|
+
:type 'directory)
|
138
|
+
|
139
|
+
(defcustom mhc-icon-setup-hook nil
|
140
|
+
"*A hook called after icon setup."
|
141
|
+
:group 'mhc
|
142
|
+
:type 'hook)
|
143
|
+
|
144
|
+
(defcustom mhc-summary-line-format
|
145
|
+
(if (eq mhc-summary-language 'japanese)
|
146
|
+
"%Y%年%M%月%D%日%(%曜%) %b%e %c%i%s %p%l"
|
147
|
+
"%Y%/%M%/%D%S%W %b%e %c%r%i%s %p%l")
|
148
|
+
"*A format string for summary line of MHC.
|
149
|
+
It may include any of the following format specifications
|
150
|
+
which are replaced by the given information:
|
151
|
+
|
152
|
+
%Y The year of the line if first line of the day.
|
153
|
+
%M The month of the line if first line of the day.
|
154
|
+
%D The day of the line if first line of the day.
|
155
|
+
%W The weekday name of the line if first line of the day.
|
156
|
+
%b Begin time.
|
157
|
+
%e End time (includes '-').
|
158
|
+
%c Warning string for conflict (See also `mhc-summary-string-conflict').
|
159
|
+
%i The icon for the schedule.
|
160
|
+
%s The subject of the schedule.
|
161
|
+
%p The priority of the schedule.
|
162
|
+
%l The location of the schedule.
|
163
|
+
%r Indicator for recurrence-tag (See also `mhc-summary-string-recurrence').
|
164
|
+
|
165
|
+
%/ A slash character if first line of the day.
|
166
|
+
%( A left parenthesis character if first line of the day.
|
167
|
+
%) A right parenthesis character if first line of the day.
|
168
|
+
%S A space with face.
|
169
|
+
|
170
|
+
%年 The '年' of the line if first line of the day.
|
171
|
+
%月 The '月' of the line if first line of the day.
|
172
|
+
%日 The '日' of the line if first line of the day.
|
173
|
+
%曜 The japaneses weekday name of the line if first line of the day.
|
174
|
+
"
|
175
|
+
:group 'mhc
|
176
|
+
:type 'string)
|
177
|
+
|
178
|
+
;;; Internal Variable:
|
179
|
+
|
180
|
+
(defconst mhc-summary-major-mode-alist
|
181
|
+
'((mew-summary-mode . mhc-mew)
|
182
|
+
(mew-virtual-mode . mhc-mew)
|
183
|
+
(wl-folder-mode . mhc-wl)
|
184
|
+
(wl-summary-mode . mhc-wl)
|
185
|
+
(gnus-group-mode . mhc-gnus)
|
186
|
+
(gnus-summary-mode . mhc-gnus)))
|
187
|
+
|
188
|
+
;; Internal Variables which are bound while inserting line:
|
189
|
+
(defvar mhc-tmp-day-face nil "a face for the day.")
|
190
|
+
(defvar mhc-tmp-dayinfo nil "a dayinfo for the day.")
|
191
|
+
(defvar mhc-tmp-schedule nil "a schedule structure.")
|
192
|
+
(defvar mhc-tmp-begin nil "begin time.")
|
193
|
+
(defvar mhc-tmp-end nil "end time.")
|
194
|
+
(defvar mhc-tmp-conflict nil "non-nil if conflicted schedule.")
|
195
|
+
(defvar mhc-tmp-recurrence nil "non-nil if recurrence schedule.")
|
196
|
+
(defvar mhc-tmp-first nil "non-nil if first schedule.")
|
197
|
+
(defvar mhc-tmp-private nil "non-nil if private display mode.")
|
198
|
+
(defvar mhc-tmp-priority nil "a priority of the schedule.")
|
199
|
+
;; For TODO.
|
200
|
+
(defvar mhc-tmp-day nil "the day.")
|
201
|
+
(defvar mhc-tmp-deadline nil "a schedule structure.")
|
202
|
+
|
203
|
+
;; Inserter (internal variable)
|
204
|
+
(defvar mhc-summary/line-inserter nil)
|
205
|
+
|
206
|
+
(defvar mhc-summary-line-format-alist
|
207
|
+
'((?Y (mhc-summary/line-year-string)
|
208
|
+
'face mhc-tmp-day-face)
|
209
|
+
(?/ (if mhc-tmp-first "/" " ")
|
210
|
+
'face mhc-tmp-day-face)
|
211
|
+
(?S " " 'face mhc-tmp-day-face)
|
212
|
+
(?M (mhc-summary/line-month-string)
|
213
|
+
'face mhc-tmp-day-face)
|
214
|
+
(?D (mhc-summary/line-day-string)
|
215
|
+
'face mhc-tmp-day-face)
|
216
|
+
(?W (mhc-summary/line-day-of-week-string)
|
217
|
+
'face mhc-tmp-day-face)
|
218
|
+
(?b (if (null mhc-tmp-begin)
|
219
|
+
(make-string 5 ? )
|
220
|
+
(format "%02d:%02d" (/ mhc-tmp-begin 60) (% mhc-tmp-begin 60)))
|
221
|
+
'face 'mhc-summary-face-time)
|
222
|
+
(?e (if (null mhc-tmp-end)
|
223
|
+
(make-string 6 ? )
|
224
|
+
(format "-%02d:%02d" (/ mhc-tmp-end 60) (% mhc-tmp-end 60)))
|
225
|
+
'face 'mhc-summary-face-time)
|
226
|
+
(?c (if mhc-tmp-conflict
|
227
|
+
(if (and (mhc-use-icon-p) (mhc-icon-exists-p "conflict"))
|
228
|
+
t
|
229
|
+
mhc-summary-string-conflict))
|
230
|
+
(if (and (mhc-use-icon-p) (mhc-icon-exists-p "conflict"))
|
231
|
+
'icon 'face)
|
232
|
+
(if (and (mhc-use-icon-p) (mhc-icon-exists-p "conflict"))
|
233
|
+
(list "conflict") 'mhc-summary-face-conflict))
|
234
|
+
(?r (if (and mhc-tmp-recurrence (not (string= "" mhc-tmp-recurrence)))
|
235
|
+
(if (and (mhc-use-icon-p) (mhc-icon-exists-p "recurrence"))
|
236
|
+
t
|
237
|
+
mhc-summary-string-recurrence))
|
238
|
+
(if (and (mhc-use-icon-p) (mhc-icon-exists-p "recurrence"))
|
239
|
+
'icon 'face)
|
240
|
+
(if (and (mhc-use-icon-p) (mhc-icon-exists-p "recurrence"))
|
241
|
+
(list "recurrence") 'mhc-summary-face-recurrence))
|
242
|
+
(?p (if mhc-tmp-priority
|
243
|
+
(format "[%d]" mhc-tmp-priority))
|
244
|
+
'face (cond
|
245
|
+
((null mhc-tmp-priority) nil)
|
246
|
+
((>= mhc-tmp-priority 80) 'mhc-summary-face-sunday)
|
247
|
+
((>= mhc-tmp-priority 50) 'mhc-summary-face-saturday)))
|
248
|
+
(?i (not mhc-tmp-private) 'icon
|
249
|
+
(if (mhc-schedule-in-category-p mhc-tmp-schedule "done")
|
250
|
+
(delete "todo"
|
251
|
+
(copy-sequence (mhc-schedule-categories mhc-tmp-schedule)))
|
252
|
+
(mhc-schedule-categories mhc-tmp-schedule)))
|
253
|
+
(?s (mhc-summary/line-subject-string)
|
254
|
+
'face
|
255
|
+
(if mhc-tmp-private (mhc-face-category-to-face "Private")
|
256
|
+
(mhc-face-category-to-face
|
257
|
+
(car (mhc-schedule-categories mhc-tmp-schedule)))))
|
258
|
+
(?l (mhc-summary/line-location-string)
|
259
|
+
'face 'mhc-summary-face-location)
|
260
|
+
(?\( (if mhc-tmp-first "(" " ")
|
261
|
+
'face mhc-tmp-day-face)
|
262
|
+
(?\) (if mhc-tmp-first ")" " ")
|
263
|
+
'face mhc-tmp-day-face)
|
264
|
+
(?年 (if mhc-tmp-first "年" (make-string 2 ? ))
|
265
|
+
'face mhc-tmp-day-face)
|
266
|
+
(?月 (if mhc-tmp-first "月" (make-string 2 ? ))
|
267
|
+
'face mhc-tmp-day-face)
|
268
|
+
(?日 (if mhc-tmp-first "日" (make-string 2 ? ))
|
269
|
+
'face mhc-tmp-day-face)
|
270
|
+
(?曜 (mhc-summary/line-day-of-week-ja-string)
|
271
|
+
'face mhc-tmp-day-face))
|
272
|
+
"An alist of format specifications that can appear in summary lines.
|
273
|
+
Each element is a list of following:
|
274
|
+
\(SPEC STRING-EXP PROP-TYPE PROP-VALUE\)
|
275
|
+
SPEC is a character for format specification.
|
276
|
+
STRING is an expression to get string to insert.
|
277
|
+
PROP-TYPE is an expression to get one of the two symbols `face' or `icon'.
|
278
|
+
It indicates a type of the property to put on the inserted string.
|
279
|
+
PROP-VALUE is the property value correspond to PROP-TYPE.
|
280
|
+
")
|
281
|
+
|
282
|
+
|
283
|
+
(defvar mhc-summary/cw-separator nil)
|
284
|
+
(defvar mhc-summary/cw-week nil)
|
285
|
+
|
286
|
+
;;; MUA Backend Functions:
|
287
|
+
|
288
|
+
;; (defun mhc-summary-mailer-type ()
|
289
|
+
;; "Return mailer backend symbol using currently."
|
290
|
+
;; (or (cdr (assq major-mode mhc-summary-major-mode-alist))
|
291
|
+
;; (intern (concat "mhc-" (symbol-name mhc-mailer-package)))))
|
292
|
+
|
293
|
+
(defun mhc-summary-mailer-type () 'mhc-mua)
|
294
|
+
|
295
|
+
(defun mhc-summary/true (&rest args)
|
296
|
+
"This is the dummy backend function, which always returns t."
|
297
|
+
t)
|
298
|
+
|
299
|
+
(defsubst mhc-summary-get-function (operation &optional mailer)
|
300
|
+
"Return appropriate function to do OPERATION for MAILER."
|
301
|
+
(or (get (require (or mailer (mhc-summary-mailer-type))) operation)
|
302
|
+
'mhc-summary/true))
|
303
|
+
|
304
|
+
(defsubst mhc-get-function (operation)
|
305
|
+
"Return appropriate function to do OPERATION."
|
306
|
+
(or (get (require (intern (concat "mhc-" (symbol-name mhc-mailer-package))))
|
307
|
+
operation)
|
308
|
+
'mhc-summary/true))
|
309
|
+
|
310
|
+
(defsubst mhc-highlight-message (&optional for-draft)
|
311
|
+
"Hilight message in the current buffer.
|
312
|
+
If optional argument FOR-DRAFT is non-nil, Hilight message as draft message."
|
313
|
+
(funcall (mhc-get-function 'highlight-message) for-draft))
|
314
|
+
|
315
|
+
(defsubst mhc-eword-decode-string (string)
|
316
|
+
"Decode encoded STRING."
|
317
|
+
(funcall (mhc-get-function 'eword-decode-string) string))
|
318
|
+
|
319
|
+
(defsubst mhc-decode-header ()
|
320
|
+
"Decode encoded header."
|
321
|
+
(funcall (mhc-get-function 'decode-header)))
|
322
|
+
|
323
|
+
(defsubst mhc-summary-filename (&optional mailer)
|
324
|
+
"Return file name of article on current line."
|
325
|
+
(funcall (mhc-summary-get-function 'summary-filename mailer)))
|
326
|
+
|
327
|
+
(defsubst mhc-summary-display-article (&optional mailer)
|
328
|
+
"Display article on current line."
|
329
|
+
(funcall (mhc-summary-get-function 'summary-display-article mailer)))
|
330
|
+
|
331
|
+
(defsubst mhc-summary-get-import-buffer (&optional get-original mailer)
|
332
|
+
"Return buffer to import article."
|
333
|
+
(funcall (mhc-summary-get-function 'get-import-buffer mailer) get-original))
|
334
|
+
|
335
|
+
(defsubst mhc-summary-generate-buffer (date &optional mailer)
|
336
|
+
"Generate buffer with summary mode of MAILER."
|
337
|
+
(funcall (mhc-summary-get-function 'generate-summary-buffer mailer) date))
|
338
|
+
|
339
|
+
(defsubst mhc-summary-insert-contents (mhc-tmp-schedule
|
340
|
+
mhc-tmp-private
|
341
|
+
inserter
|
342
|
+
&optional mailer)
|
343
|
+
(if (eq 'direct mailer)
|
344
|
+
(let ((mhc-use-icon nil))
|
345
|
+
(mhc-summary-line-insert)
|
346
|
+
(insert "\n"))
|
347
|
+
(funcall (mhc-summary-get-function 'insert-summary-contents mailer)
|
348
|
+
inserter)))
|
349
|
+
|
350
|
+
(defsubst mhc-summary-search-date (date)
|
351
|
+
"Search day in the current buffer."
|
352
|
+
(let (dayinfo)
|
353
|
+
(goto-char (point-min))
|
354
|
+
(while (and (not (eobp))
|
355
|
+
(or (null (setq dayinfo
|
356
|
+
(get-text-property (point) 'mhc-dayinfo)))
|
357
|
+
(not (eq (mhc-day-date dayinfo) date))))
|
358
|
+
(goto-char (next-single-property-change (point) 'mhc-dayinfo)))))
|
359
|
+
|
360
|
+
(defsubst mhc-summary-mode-setup (date &optional mailer)
|
361
|
+
"Setup buffer as summary mode of MAILER."
|
362
|
+
(funcall (mhc-summary-get-function 'summary-mode-setup mailer) date))
|
363
|
+
|
364
|
+
(defun mhc-summary-record (&optional mailer)
|
365
|
+
"Return record on current line."
|
366
|
+
(let ((filename (mhc-summary-filename mailer)))
|
367
|
+
(if filename
|
368
|
+
(mhc-parse-file filename))))
|
369
|
+
|
370
|
+
;;; Codes:
|
371
|
+
(defsubst mhc-summary/make-string (count character)
|
372
|
+
(make-string (max 4 count) character)) ;; xxxx 4 ?
|
373
|
+
|
374
|
+
|
375
|
+
(defun mhc-summary/insert-separator (&optional char banner width)
|
376
|
+
"Insert horizontal using CHAR in WIDTH.
|
377
|
+
CHAR is '-' if not specified. default WIDTH is calculated from window size.
|
378
|
+
If BANNER is set, it is printed on the horizontal line."
|
379
|
+
(let ((hr (make-string (or width (- (mhc-misc-get-width) 2)) (or char ?-)))
|
380
|
+
(bn (or banner ""))
|
381
|
+
(bn-offset 4))
|
382
|
+
(mhc-face-put hr 'mhc-summary-face-separator)
|
383
|
+
(mhc-face-put bn 'mhc-summary-face-cw)
|
384
|
+
(insert
|
385
|
+
(concat
|
386
|
+
(substring hr 0 bn-offset)
|
387
|
+
bn
|
388
|
+
(substring hr (+ bn-offset (length bn)) -1)
|
389
|
+
"\n"))))
|
390
|
+
|
391
|
+
(defvar mhc-summary/today nil)
|
392
|
+
|
393
|
+
(defun mhc-summary/insert-dayinfo (mhc-tmp-dayinfo mailer category-predicate secret)
|
394
|
+
(let ((time-max -1)
|
395
|
+
(schedules (mhc-day-schedules mhc-tmp-dayinfo))
|
396
|
+
(mhc-tmp-first t)
|
397
|
+
mhc-tmp-begin mhc-tmp-end
|
398
|
+
mhc-tmp-location mhc-tmp-schedule
|
399
|
+
mhc-tmp-conflict mhc-tmp-recurrence mhc-tmp-priority
|
400
|
+
next-begin displayed)
|
401
|
+
(if schedules
|
402
|
+
(progn
|
403
|
+
(while schedules
|
404
|
+
(if (funcall category-predicate (car schedules))
|
405
|
+
(progn
|
406
|
+
(setq mhc-tmp-begin (mhc-schedule-time-begin (car schedules))
|
407
|
+
mhc-tmp-end (mhc-schedule-time-end (car schedules))
|
408
|
+
mhc-tmp-priority (mhc-schedule-priority
|
409
|
+
(car schedules))
|
410
|
+
next-begin (if (car (cdr schedules))
|
411
|
+
(mhc-schedule-time-begin
|
412
|
+
(car (cdr schedules))))
|
413
|
+
mhc-tmp-conflict (or (and mhc-tmp-end next-begin
|
414
|
+
(< next-begin mhc-tmp-end))
|
415
|
+
(and mhc-tmp-begin time-max
|
416
|
+
(< mhc-tmp-begin time-max)))
|
417
|
+
mhc-tmp-recurrence (mhc-schedule-recurrence-tag (car schedules)))
|
418
|
+
(if mhc-tmp-end (setq time-max (max mhc-tmp-end time-max)))
|
419
|
+
(setq displayed t)
|
420
|
+
(mhc-summary-insert-contents
|
421
|
+
(car schedules)
|
422
|
+
(and secret
|
423
|
+
(mhc-schedule-in-category-p
|
424
|
+
(car schedules) mhc-category-as-private))
|
425
|
+
'mhc-summary-line-insert
|
426
|
+
mailer)
|
427
|
+
(setq mhc-tmp-first nil)))
|
428
|
+
(setq schedules (cdr schedules)))
|
429
|
+
(if (not displayed)
|
430
|
+
(mhc-summary-insert-contents nil secret
|
431
|
+
'mhc-summary-line-insert
|
432
|
+
mailer)))
|
433
|
+
(mhc-summary-insert-contents nil secret
|
434
|
+
'mhc-summary-line-insert
|
435
|
+
mailer))))
|
436
|
+
|
437
|
+
|
438
|
+
(defun mhc-summary-make-contents
|
439
|
+
(dayinfo-list &optional from to mailer category-predicate secret)
|
440
|
+
(let* ((sparse (or from to))
|
441
|
+
(from (or from (mhc-day-date (car dayinfo-list))))
|
442
|
+
(to (or to (mhc-day-date (car (last dayinfo-list)))))
|
443
|
+
(date from) dayinfo
|
444
|
+
(separator-format (and mhc-summary-use-cw
|
445
|
+
mhc-use-week-separator
|
446
|
+
(eq mhc-start-day-of-week 1)
|
447
|
+
" CW %d ")))
|
448
|
+
(while (mhc-date<= date to)
|
449
|
+
(setq dayinfo (or (assoc date dayinfo-list)
|
450
|
+
(and sparse (mhc-day-new date))))
|
451
|
+
(when dayinfo
|
452
|
+
(mhc-summary/insert-dayinfo
|
453
|
+
dayinfo
|
454
|
+
(or mailer 'mhc-mua)
|
455
|
+
(or category-predicate mhc-default-category-predicate-sexp)
|
456
|
+
secret))
|
457
|
+
(setq date (mhc-date++ date))
|
458
|
+
;; insert week separator
|
459
|
+
(and sparse mhc-use-week-separator
|
460
|
+
(eq (mhc-date-ww date) mhc-start-day-of-week)
|
461
|
+
(mhc-summary/insert-separator
|
462
|
+
mhc-summary-separator
|
463
|
+
(and separator-format (format separator-format (mhc-date-cw date)))))
|
464
|
+
;; insert month separator
|
465
|
+
(and sparse mhc-use-month-separator
|
466
|
+
(eq (mhc-date-dd date) 1)
|
467
|
+
(mhc-summary/insert-separator
|
468
|
+
mhc-summary-month-separator)))))
|
469
|
+
|
470
|
+
(defun mhc-summary/line-year-string ()
|
471
|
+
(if mhc-tmp-first
|
472
|
+
(format "%4d" (mhc-day-year mhc-tmp-dayinfo))
|
473
|
+
(make-string 4 ? )))
|
474
|
+
|
475
|
+
|
476
|
+
(defun mhc-summary/line-month-string ()
|
477
|
+
(if mhc-tmp-first
|
478
|
+
(format "%02d" (mhc-day-month mhc-tmp-dayinfo))
|
479
|
+
(make-string 2 ? )))
|
480
|
+
|
481
|
+
|
482
|
+
(defun mhc-summary/line-day-string ()
|
483
|
+
(if mhc-tmp-first
|
484
|
+
(format "%02d" (mhc-day-day-of-month mhc-tmp-dayinfo))
|
485
|
+
(make-string 2 ? )))
|
486
|
+
|
487
|
+
|
488
|
+
(defun mhc-summary/line-day-of-week-string ()
|
489
|
+
(if mhc-tmp-first
|
490
|
+
(let ((week (mhc-day-day-of-week mhc-tmp-dayinfo)))
|
491
|
+
(if (and mhc-summary/cw-week (= week 1) )
|
492
|
+
(format "%3s"
|
493
|
+
(format "w%d" (mhc-date-cw (mhc-day-date mhc-tmp-dayinfo))))
|
494
|
+
(aref ["Sun" "Mon" "Tue" "Wed" "Thu" "Fri" "Sat"] week)))
|
495
|
+
(make-string 3 ? )))
|
496
|
+
|
497
|
+
(defun mhc-summary/line-day-of-week-ja-string ()
|
498
|
+
(if mhc-tmp-first
|
499
|
+
(let ((week (mhc-day-day-of-week mhc-tmp-dayinfo)))
|
500
|
+
(if (and mhc-summary/cw-week(= week 1) )
|
501
|
+
(format "%2d" (mhc-date-cw (mhc-day-date mhc-tmp-dayinfo)))
|
502
|
+
(aref ["日" "月" "火" "水" "木" "金" "土"] week)))
|
503
|
+
(make-string 2 ? )))
|
504
|
+
|
505
|
+
|
506
|
+
(defun mhc-summary/line-subject-string ()
|
507
|
+
(if mhc-tmp-private
|
508
|
+
(and mhc-tmp-schedule mhc-summary-string-secret)
|
509
|
+
(or (mhc-schedule-subject mhc-tmp-schedule) "")))
|
510
|
+
|
511
|
+
|
512
|
+
(defun mhc-summary/line-location-string ()
|
513
|
+
(let ((location (mhc-schedule-location mhc-tmp-schedule)))
|
514
|
+
(and (not mhc-tmp-private)
|
515
|
+
location
|
516
|
+
(> (length location) 0)
|
517
|
+
(concat "[" location "]"))))
|
518
|
+
|
519
|
+
|
520
|
+
;;; Line format parsing
|
521
|
+
|
522
|
+
(defmacro mhc-line-insert (string)
|
523
|
+
`(and (stringp ,string) (insert ,string)))
|
524
|
+
|
525
|
+
(defun mhc-line-parse-format (format spec-alist)
|
526
|
+
(let ((f (mhc-string-to-char-list format))
|
527
|
+
inserter entry)
|
528
|
+
(setq inserter (list 'let (list 'pos)))
|
529
|
+
(while f
|
530
|
+
(if (eq (car f) ?%)
|
531
|
+
(progn
|
532
|
+
(setq f (cdr f))
|
533
|
+
(if (eq (car f) ?%)
|
534
|
+
(setq inserter (append inserter (list (list 'insert ?%))))
|
535
|
+
(setq entry (assq (car f) spec-alist))
|
536
|
+
(unless entry
|
537
|
+
(error "Unknown format spec %%%c" (car f)))
|
538
|
+
(setq inserter
|
539
|
+
(append inserter
|
540
|
+
(list (list 'setq 'pos (list 'point)))
|
541
|
+
(list (list 'mhc-line-insert
|
542
|
+
(nth 1 entry)))
|
543
|
+
(and
|
544
|
+
(nth 2 entry)
|
545
|
+
(list
|
546
|
+
(append (cond
|
547
|
+
((eq (eval (nth 2 entry)) 'face)
|
548
|
+
(list 'put-text-property
|
549
|
+
'pos (list 'point)
|
550
|
+
(list 'quote 'face)
|
551
|
+
(nth 3 entry)))
|
552
|
+
((eq (eval (nth 2 entry)) 'icon)
|
553
|
+
(list 'if
|
554
|
+
(nth 1 entry)
|
555
|
+
(list
|
556
|
+
'and
|
557
|
+
(list 'mhc-use-icon-p)
|
558
|
+
(list 'mhc-put-icon
|
559
|
+
(nth 3 entry)))))))))))))
|
560
|
+
(setq inserter (append inserter (list (list 'insert (car f))))))
|
561
|
+
(setq f (cdr f)))
|
562
|
+
inserter))
|
563
|
+
|
564
|
+
|
565
|
+
(defmacro mhc-line-inserter-setup (inserter format alist)
|
566
|
+
`(let (byte-compile-warnings)
|
567
|
+
(setq ,inserter
|
568
|
+
(byte-compile
|
569
|
+
(list 'lambda ()
|
570
|
+
(mhc-line-parse-format ,format ,alist))))
|
571
|
+
(when (get-buffer "*Compile-Log*")
|
572
|
+
(bury-buffer "*Compile-Log*"))
|
573
|
+
(when (get-buffer "*Compile-Log-Show*")
|
574
|
+
(bury-buffer "*Compile-Log-Show*"))))
|
575
|
+
|
576
|
+
|
577
|
+
(defun mhc-summary-line-inserter-setup ()
|
578
|
+
"Setup MHC summary and line inserter."
|
579
|
+
(interactive)
|
580
|
+
(if (and (called-interactively-p 'interactive)
|
581
|
+
(mhc-use-icon-p))
|
582
|
+
(call-interactively 'mhc-icon-setup))
|
583
|
+
(setq mhc-summary/cw-separator (and mhc-summary-use-cw
|
584
|
+
mhc-use-week-separator
|
585
|
+
(eq mhc-start-day-of-week 1)))
|
586
|
+
(setq mhc-summary/cw-week (and mhc-summary-use-cw
|
587
|
+
(not mhc-summary/cw-separator)))
|
588
|
+
(mhc-line-inserter-setup
|
589
|
+
mhc-summary/line-inserter
|
590
|
+
mhc-summary-line-format
|
591
|
+
mhc-summary-line-format-alist))
|
592
|
+
|
593
|
+
|
594
|
+
(defun mhc-summary-line-insert ()
|
595
|
+
"Insert summary line."
|
596
|
+
(let ((mhc-tmp-day-face (cond
|
597
|
+
((mhc-schedule-in-category-p
|
598
|
+
mhc-tmp-schedule "holiday")
|
599
|
+
'mhc-category-face-holiday)
|
600
|
+
((eq (mhc-day-day-of-week
|
601
|
+
mhc-tmp-dayinfo) 0)
|
602
|
+
'mhc-summary-face-sunday)
|
603
|
+
((eq (mhc-day-day-of-week mhc-tmp-dayinfo) 6)
|
604
|
+
'mhc-summary-face-saturday)
|
605
|
+
(t 'mhc-summary-face-default)))
|
606
|
+
(pos (point)))
|
607
|
+
(if (mhc-date= (mhc-day-date mhc-tmp-dayinfo) (mhc-date-now))
|
608
|
+
(setq mhc-tmp-day-face (mhc-face-get-today-face mhc-tmp-day-face)))
|
609
|
+
(funcall mhc-summary/line-inserter)
|
610
|
+
(put-text-property pos (point) 'mhc-dayinfo mhc-tmp-dayinfo)))
|
611
|
+
|
612
|
+
|
613
|
+
(defvar mhc-summary-mode-map nil)
|
614
|
+
|
615
|
+
;; (unless mhc-summary-mode-map
|
616
|
+
(setq mhc-summary-mode-map (make-sparse-keymap))
|
617
|
+
(define-key mhc-summary-mode-map " " 'mhc-summary-scroll-message-forward)
|
618
|
+
(define-key mhc-summary-mode-map (kbd "DEL") 'mhc-summary-scroll-message-backward)
|
619
|
+
(define-key mhc-summary-mode-map "." 'mhc-summary-display)
|
620
|
+
(define-key mhc-summary-mode-map "\C-m" 'mhc-summary-scroll-message-line-forward)
|
621
|
+
(define-key mhc-summary-mode-map "v" 'mhc-summary-toggle-display-message)
|
622
|
+
|
623
|
+
(define-key mhc-summary-mode-map "g" 'mhc-goto-month)
|
624
|
+
(define-key mhc-summary-mode-map "/" 'mhc-search)
|
625
|
+
(define-key mhc-summary-mode-map ">" 'mhc-goto-next-month)
|
626
|
+
(define-key mhc-summary-mode-map "N" 'mhc-goto-next-year)
|
627
|
+
(define-key mhc-summary-mode-map "<" 'mhc-goto-prev-month)
|
628
|
+
(define-key mhc-summary-mode-map "P" 'mhc-goto-prev-year)
|
629
|
+
|
630
|
+
(define-key mhc-summary-mode-map "s" 'mhc-rescan-month)
|
631
|
+
(define-key mhc-summary-mode-map "d" 'mhc-delete)
|
632
|
+
(define-key mhc-summary-mode-map "c" 'mhc-set-default-category)
|
633
|
+
(define-key mhc-summary-mode-map "?" 'mhc-calendar)
|
634
|
+
(define-key mhc-summary-mode-map "t" 'mhc-calendar-toggle-insert-rectangle)
|
635
|
+
(define-key mhc-summary-mode-map "E" 'mhc-edit)
|
636
|
+
(define-key mhc-summary-mode-map "M" 'mhc-modify)
|
637
|
+
|
638
|
+
(define-key mhc-summary-mode-map "n" 'mhc-summary-display-next)
|
639
|
+
(define-key mhc-summary-mode-map "p" 'mhc-summary-display-previous)
|
640
|
+
(define-key mhc-summary-mode-map "f" 'forward-char)
|
641
|
+
(define-key mhc-summary-mode-map "b" 'backward-char)
|
642
|
+
|
643
|
+
(define-key mhc-summary-mode-map "j" 'mhc-summary-display-next)
|
644
|
+
(define-key mhc-summary-mode-map "k" 'mhc-summary-display-previous)
|
645
|
+
(define-key mhc-summary-mode-map "l" 'forward-char)
|
646
|
+
(define-key mhc-summary-mode-map "h" 'backward-char)
|
647
|
+
;; )
|
648
|
+
|
649
|
+
(defun mhc-summary-mode ()
|
650
|
+
"Major mode for MHC summary.
|
651
|
+
|
652
|
+
\\{mhc-summary-mode-map}"
|
653
|
+
(interactive)
|
654
|
+
(setq major-mode 'mhc-summary-mode
|
655
|
+
mode-name "MHC")
|
656
|
+
(setq mode-line-buffer-identification (propertized-buffer-identification
|
657
|
+
"MHC: %12b"))
|
658
|
+
(set-buffer-modified-p nil)
|
659
|
+
(setq buffer-read-only t)
|
660
|
+
(setq inhibit-read-only nil)
|
661
|
+
(setq truncate-lines t)
|
662
|
+
(use-local-map mhc-summary-mode-map)
|
663
|
+
(run-hooks 'mhc-summary-mode-hook))
|
664
|
+
|
665
|
+
(defun mhc-summary-display-message ()
|
666
|
+
(interactive)
|
667
|
+
(save-selected-window
|
668
|
+
(mhc-summary-display-article)))
|
669
|
+
|
670
|
+
(defun mhc-summary-toggle-display-message ()
|
671
|
+
(interactive)
|
672
|
+
(if (mhc-message-visible-p)
|
673
|
+
(mhc-message-delete-windows)
|
674
|
+
(mhc-summary-display-message)))
|
675
|
+
|
676
|
+
(defvar mhc-message-file-name nil)
|
677
|
+
(make-variable-buffer-local 'mhc-message-file-name)
|
678
|
+
|
679
|
+
(defun mhc-message-set-file-name (file-name)
|
680
|
+
(setq mhc-message-file-name file-name))
|
681
|
+
|
682
|
+
(defun mhc-message-visible-p (&optional file-name)
|
683
|
+
"Return non-nil if MHC message is currently displaying, or nil if none."
|
684
|
+
(and (get-buffer-window "*MHC message*")
|
685
|
+
(or (null file-name)
|
686
|
+
(save-selected-window
|
687
|
+
(pop-to-buffer "*MHC message*")
|
688
|
+
(and (stringp mhc-message-file-name)
|
689
|
+
(string= mhc-message-file-name file-name))))))
|
690
|
+
|
691
|
+
(defun mhc-message-delete-windows ()
|
692
|
+
(delete-windows-on "*MHC message*"))
|
693
|
+
|
694
|
+
(defalias 'mhc-summary-display 'mhc-summary-display-message)
|
695
|
+
|
696
|
+
(defun mhc-summary-display-next ()
|
697
|
+
(interactive)
|
698
|
+
(forward-line)
|
699
|
+
(if (mhc-message-visible-p)
|
700
|
+
(mhc-summary-display)))
|
701
|
+
|
702
|
+
(defun mhc-summary-display-previous ()
|
703
|
+
(interactive)
|
704
|
+
(forward-line -1)
|
705
|
+
(if (mhc-message-visible-p)
|
706
|
+
(mhc-summary-display)))
|
707
|
+
|
708
|
+
(defun mhc-summary-scroll-message-line-forward ()
|
709
|
+
(interactive)
|
710
|
+
(mhc-summary-scroll-message-forward 1))
|
711
|
+
|
712
|
+
(defun mhc-summary-scroll-message-forward (&optional lines)
|
713
|
+
(interactive)
|
714
|
+
(mhc-summary-scroll-message 'forward lines))
|
715
|
+
|
716
|
+
(defun mhc-summary-scroll-message-backward (&optional lines)
|
717
|
+
(interactive)
|
718
|
+
(mhc-summary-scroll-message 'backward lines))
|
719
|
+
|
720
|
+
(defun mhc-summary-scroll-message (direction &optional lines)
|
721
|
+
(interactive)
|
722
|
+
(if (mhc-message-visible-p (mhc-summary-filename))
|
723
|
+
(save-selected-window
|
724
|
+
(pop-to-buffer "*MHC message*")
|
725
|
+
(if (eq direction 'forward)
|
726
|
+
(mhc-message-scroll-page-forward lines)
|
727
|
+
(mhc-message-scroll-page-backward lines)))
|
728
|
+
(mhc-summary-display-message)))
|
729
|
+
|
730
|
+
(provide 'mhc-summary)
|
731
|
+
|
732
|
+
;;; Copyright Notice:
|
733
|
+
|
734
|
+
;; Copyright (C) 1999, 2000 Yoshinari Nomura. All rights reserved.
|
735
|
+
;; Copyright (C) 2000 MHC developing team. All rights reserved.
|
736
|
+
|
737
|
+
;; Redistribution and use in source and binary forms, with or without
|
738
|
+
;; modification, are permitted provided that the following conditions
|
739
|
+
;; are met:
|
740
|
+
;;
|
741
|
+
;; 1. Redistributions of source code must retain the above copyright
|
742
|
+
;; notice, this list of conditions and the following disclaimer.
|
743
|
+
;; 2. Redistributions in binary form must reproduce the above copyright
|
744
|
+
;; notice, this list of conditions and the following disclaimer in the
|
745
|
+
;; documentation and/or other materials provided with the distribution.
|
746
|
+
;; 3. Neither the name of the team nor the names of its contributors
|
747
|
+
;; may be used to endorse or promote products derived from this software
|
748
|
+
;; without specific prior written permission.
|
749
|
+
;;
|
750
|
+
;; THIS SOFTWARE IS PROVIDED BY THE TEAM AND CONTRIBUTORS ``AS IS''
|
751
|
+
;; AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
752
|
+
;; LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
|
753
|
+
;; FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
|
754
|
+
;; THE TEAM OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
755
|
+
;; INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
756
|
+
;; (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
757
|
+
;; SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
758
|
+
;; HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
759
|
+
;; STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
760
|
+
;; ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
|
761
|
+
;; OF THE POSSIBILITY OF SUCH DAMAGE.
|
762
|
+
|
763
|
+
;;; mhc-summary.el ends here.
|