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.
Files changed (127) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +27 -0
  3. data/.rspec +2 -0
  4. data/.travis.yml +3 -0
  5. data/COPYRIGHT +28 -0
  6. data/Gemfile +8 -0
  7. data/README.org +209 -0
  8. data/Rakefile +13 -0
  9. data/bin/mhc +312 -0
  10. data/emacs/Cask +25 -0
  11. data/emacs/Makefile +58 -0
  12. data/emacs/mhc-calendar.el +1723 -0
  13. data/emacs/mhc-calfw.el +135 -0
  14. data/emacs/mhc-compat.el +90 -0
  15. data/emacs/mhc-date.el +642 -0
  16. data/emacs/mhc-day.el +149 -0
  17. data/emacs/mhc-db.el +158 -0
  18. data/emacs/mhc-draft.el +211 -0
  19. data/emacs/mhc-e21.el +167 -0
  20. data/emacs/mhc-face.el +236 -0
  21. data/emacs/mhc-file.el +224 -0
  22. data/emacs/mhc-guess.el +648 -0
  23. data/emacs/mhc-header.el +176 -0
  24. data/emacs/mhc-logic.el +563 -0
  25. data/emacs/mhc-message.el +130 -0
  26. data/emacs/mhc-minibuf.el +466 -0
  27. data/emacs/mhc-misc.el +248 -0
  28. data/emacs/mhc-mua.el +260 -0
  29. data/emacs/mhc-parse.el +286 -0
  30. data/emacs/mhc-process.el +35 -0
  31. data/emacs/mhc-ps.el +1174 -0
  32. data/emacs/mhc-record.el +201 -0
  33. data/emacs/mhc-schedule.el +202 -0
  34. data/emacs/mhc-summary.el +763 -0
  35. data/emacs/mhc-sync.el +158 -0
  36. data/emacs/mhc-vars.el +149 -0
  37. data/emacs/mhc.el +1114 -0
  38. data/icons/Anniversary.xbm +6 -0
  39. data/icons/Anniversary.xpm +27 -0
  40. data/icons/Birthday.xbm +6 -0
  41. data/icons/Birthday.xpm +25 -0
  42. data/icons/Business.xbm +6 -0
  43. data/icons/Business.xpm +24 -0
  44. data/icons/CheckBox.xbm +6 -0
  45. data/icons/CheckBox.xpm +24 -0
  46. data/icons/CheckedBox.xbm +6 -0
  47. data/icons/CheckedBox.xpm +25 -0
  48. data/icons/Conflict.xbm +6 -0
  49. data/icons/Conflict.xpm +22 -0
  50. data/icons/Date.xbm +6 -0
  51. data/icons/Date.xpm +29 -0
  52. data/icons/Holiday.xbm +6 -0
  53. data/icons/Holiday.xpm +25 -0
  54. data/icons/Link.xbm +6 -0
  55. data/icons/Link.xpm +25 -0
  56. data/icons/Other.xbm +6 -0
  57. data/icons/Other.xpm +28 -0
  58. data/icons/Party.xbm +6 -0
  59. data/icons/Party.xpm +23 -0
  60. data/icons/Private.xbm +6 -0
  61. data/icons/Private.xpm +26 -0
  62. data/icons/Recurrence.xbm +6 -0
  63. data/icons/Recurrence.xpm +98 -0
  64. data/icons/Vacation.xbm +6 -0
  65. data/icons/Vacation.xpm +26 -0
  66. data/lib/mhc.rb +45 -0
  67. data/lib/mhc/builder.rb +64 -0
  68. data/lib/mhc/caldav.rb +304 -0
  69. data/lib/mhc/calendar.rb +106 -0
  70. data/lib/mhc/command.rb +13 -0
  71. data/lib/mhc/command/cache.rb +14 -0
  72. data/lib/mhc/command/completions.rb +108 -0
  73. data/lib/mhc/command/init.rb +133 -0
  74. data/lib/mhc/command/scan.rb +33 -0
  75. data/lib/mhc/command/sync.rb +22 -0
  76. data/lib/mhc/config.rb +229 -0
  77. data/lib/mhc/converter.rb +330 -0
  78. data/lib/mhc/datastore.rb +164 -0
  79. data/lib/mhc/date_enumerator.rb +274 -0
  80. data/lib/mhc/date_frame.rb +124 -0
  81. data/lib/mhc/date_helper.rb +49 -0
  82. data/lib/mhc/etag.rb +68 -0
  83. data/lib/mhc/event.rb +396 -0
  84. data/lib/mhc/formatter.rb +312 -0
  85. data/lib/mhc/logger.rb +94 -0
  86. data/lib/mhc/modifier.rb +149 -0
  87. data/lib/mhc/occurrence.rb +94 -0
  88. data/lib/mhc/occurrence_enumerator.rb +113 -0
  89. data/lib/mhc/property_value.rb +33 -0
  90. data/lib/mhc/property_value/date.rb +190 -0
  91. data/lib/mhc/property_value/integer.rb +15 -0
  92. data/lib/mhc/property_value/list.rb +41 -0
  93. data/lib/mhc/property_value/period.rb +49 -0
  94. data/lib/mhc/property_value/range.rb +100 -0
  95. data/lib/mhc/property_value/recurrence_condition.rb +272 -0
  96. data/lib/mhc/property_value/text.rb +11 -0
  97. data/lib/mhc/property_value/time.rb +45 -0
  98. data/lib/mhc/query.rb +210 -0
  99. data/lib/mhc/sync.rb +46 -0
  100. data/lib/mhc/sync/driver.rb +108 -0
  101. data/lib/mhc/sync/status.rb +70 -0
  102. data/lib/mhc/sync/status_manager.rb +142 -0
  103. data/lib/mhc/sync/strategy.rb +233 -0
  104. data/lib/mhc/sync/syncinfo.rb +98 -0
  105. data/lib/mhc/templates/config.yml.erb +142 -0
  106. data/lib/mhc/version.rb +4 -0
  107. data/lib/mhc/webdav.rb +319 -0
  108. data/mhc.gemspec +24 -0
  109. data/samples/DOT.mhc-config.yml +116 -0
  110. data/samples/japanese-holidays.mhcc +153 -0
  111. data/samples/mhc-completions.zsh +11 -0
  112. data/spec/mhc_spec.rb +682 -0
  113. data/spec/spec_helper.rb +9 -0
  114. data/xpm/close.xpm +18 -0
  115. data/xpm/delete.xpm +19 -0
  116. data/xpm/exit.xpm +18 -0
  117. data/xpm/month.xpm +18 -0
  118. data/xpm/next.xpm +18 -0
  119. data/xpm/next2.xpm +18 -0
  120. data/xpm/next_year.xpm +18 -0
  121. data/xpm/open.xpm +19 -0
  122. data/xpm/prev.xpm +18 -0
  123. data/xpm/prev2.xpm +18 -0
  124. data/xpm/prev_year.xpm +18 -0
  125. data/xpm/save.xpm +19 -0
  126. data/xpm/today.xpm +18 -0
  127. metadata +214 -0
@@ -0,0 +1,648 @@
1
+ ;;; mhc-guess.el -- Guess the important date from a Japanese mail article.
2
+
3
+ ;; Author: Yoshinari Nomura <nom@quickhack.net>
4
+ ;;
5
+ ;; Created: 1999/04/13
6
+ ;; Revised: $Date: 2007/12/05 04:59:35 $
7
+ ;;
8
+
9
+ ;;;
10
+ ;;; Commentary:
11
+ ;;;
12
+
13
+ ;;
14
+ ;; バッファから mhc-guess-{time,date}: 日付、時間を集めて、
15
+ ;; 予定の日付けを表わしていると思われる可能性の高い順に並べて
16
+ ;; 返す。
17
+ ;;
18
+ ;; 以下のような GUESS-CANDIDATE のリストを返す
19
+ ;; ([mhc-{date,time} mhc-{date,time}-end point-begin point-end score]..)
20
+ ;;
21
+ ;; mhc-{date,time}: 予定の開始 {日, 時間}
22
+ ;; mhc-{date,time}-end 予定の終了 {日, 時間} or nil
23
+ ;;
24
+ ;; 日付推測の手順
25
+ ;;
26
+ ;; 1. 日付/時刻を表すキーワード見付けて、発見個所リストを作る。
27
+ ;;
28
+ ;; (mhc-guess/gather-candidate mhc-guess-date-regexp-list now)
29
+ ;; (mhc-guess/gather-candidate mhc-guess-time-regexp-list now)
30
+ ;;
31
+ ;; の 2つの関数で、
32
+ ;;
33
+ ;; ([found-date found-date-end found-point-begin found-point-end nil] ...)
34
+ ;; ([found-time found-time-end found-point-begin found-point-end nil] ...)
35
+ ;;
36
+ ;; のような candidate-list を得る。
37
+ ;;
38
+ ;; 2. みつかった日付時刻に点数をつける。
39
+ ;;
40
+ ;; (mhc-guess/score candidate-list mhc-guess-keyword-score-alist)
41
+ ;;
42
+ ;; ([found-date found-date-end found-point-begin found-point-end score] ...)
43
+ ;;
44
+ ;; キーワードが引用行中にある
45
+ ;; 同一行に特定の文字列がある
46
+ ;; ある範囲の前方/後方に特定の文字列がある
47
+ ;;
48
+ ;; のような条件と加点/減点を表す mhc-guess-keyword-score-alist に基
49
+ ;; づいて採点をする。
50
+ ;;
51
+ ;; 3. 得点順 (得点が同じ場合は,日付や時間を表わす文字列が長い順)
52
+ ;; に sort して返す
53
+
54
+ ;;;
55
+ ;;; Code:
56
+ ;;;
57
+
58
+ (require 'mhc-date)
59
+ (provide 'mhc-guess)
60
+
61
+ ;;; Customize variables:
62
+
63
+ (defcustom mhc-guess-ignore-english-date nil
64
+ "*Ignore English dates."
65
+ :group 'mhc
66
+ :type '(choice (const :tag "Ignore" t)
67
+ (const :tag "Don't Ignore" nil)))
68
+
69
+ (defcustom mhc-guess-english-date-format '(usa)
70
+ "*English date formats.
71
+ You can specify following symbols as a list.
72
+ usa: Suppose the USA style date formats. (e.g. Feb 25, 2004)
73
+ british: Suppose British style date formats. (e.g. 25 Feb, 2004)"
74
+ :group 'mhc
75
+ :type '(repeat (choice (const :tag "USA" usa)
76
+ (const :tag "British" british))))
77
+
78
+ ;;
79
+ ;; regexp for get date strings.
80
+ ;;
81
+
82
+ (defvar mhc-guess-date-regexp-list
83
+ `(
84
+ (,(concat "\\([0-90-9][0-90-9][0-90-9][0-90-9]\\)[-−//]"
85
+ "\\([0-90-9][0-90-9]\\)[-−//]"
86
+ "\\([0-90-9][0-90-9]\\)")
87
+ mhc-guess/make-date-from-yyyymmdd 1 2 3)
88
+
89
+ (,(concat "\\([0-90-9]+年\\)?"
90
+ "\\([来今0-90-9]+\\)[\n  ]*月[\n  ]*の?[\n  ]*"
91
+ "\\([0-90-9]+\\)日?"
92
+ "\\([()()月火水木金土日曜\n   ]*"
93
+ "\\([〜−,,、-]\\|から\\|より\\)[\n  ]*"
94
+ "\\([0-90-9]+年\\)?"
95
+ "\\(\\([来今0-90-9]+\\)[\n  ]*月\\)?[\n  ]*の?[\n  ]*"
96
+ "\\([0-90-9]+\\)日?\\(間\\)?"
97
+ "\\)?")
98
+ mhc-guess/make-date-from-mmdd 2 3 8 9 10)
99
+
100
+ (,(concat "\\([0-90-9]+[  ]*[//][  ]*\\)?"
101
+ "\\([0-90-9]+\\)[  ]*[//][  ]*\\([0-90-9]+\\)"
102
+ "\\([()()月火水木金土日曜\n   ]*"
103
+ "\\([〜−,,、-]\\|から\\|より\\)[\n  ]*"
104
+ "\\([0-90-9]+[  ]*[//][  ]*\\)?"
105
+ "\\(\\([0-90-9]+\\)[  ]*[//][  ]*\\)"
106
+ "\\([0-90-9]+\\)日?\\(間\\)?"
107
+ "\\)?")
108
+ mhc-guess/make-date-from-mmdd 2 3 8 9 10)
109
+
110
+ ;; USA style date format
111
+ (,(concat "\\(Jan\\(uary\\)?\\|Feb\\(ruary\\)?\\|Mar\\(ch\\)?\\|"
112
+ "Apr\\(il\\)?\\|May\\|June?\\|July?\\|Aug\\(ust\\)?\\|"
113
+ "Sep\\(tember\\)?\\|Oct\\(ober\\)?\\|"
114
+ "Nov\\(ember\\)?\\|Dec\\(ember\\)?\\)"
115
+ "\.?,? +"
116
+ "\\([0-9][0-9]?\\)\\(st\\|nd\\rd\\|th\\)?,?[ \n]+" ;; day
117
+ "\\(\\('\\|[1-9][0-9]\\)?[0-9][0-9]\\)?") ;; year
118
+ mhc-guess/make-date-from-usa-style-date 1 11 13)
119
+
120
+ ;; British style date format
121
+ (,(concat "\\([0-9][0-9]?\\)\\(st\\|nd\\rd\\|th\\)?,? " ;; day
122
+ "\\(Jan\\(uary\\)?\\|Feb\\(ruary\\)?\\|Mar\\(ch\\)?\\|"
123
+ "Apr\\(il\\)?\\|May\\|June?\\|July?\\|Aug\\(ust\\)?\\|"
124
+ "Sep\\(tember\\)?\\|Oct\\(ober\\)?\\|"
125
+ "Nov\\(ember\\)?\\|Dec\\(ember\\)?\\)"
126
+ "\.?,?[ \n]+"
127
+ "\\(\\('\\|[1-9][0-9]\\)?[0-9][0-9]\\)?") ;; year
128
+ mhc-guess/make-date-from-british-style-date 1 3 13)
129
+
130
+ throw
131
+
132
+ (,(concat "\\(今度\\|[今来次]週\\|再来週\\)[\n  ]*の?[\n  ]*"
133
+ "\\([月火水木金土日]\\)曜")
134
+ mhc-guess/make-date-from-relative-week 1 2)
135
+
136
+ (,(concat "\\([Tt]his\\|[Nn]ext\\)[\n ]+"
137
+ "\\(Monday\\|Tuesday\\|Wednesday\\|Thursday\\|Friday\\|"
138
+ "Saturday\\|Sunday\\)")
139
+ mhc-guess/make-date-from-english-relative-week 2 1 nil)
140
+
141
+ (,(concat "\\(Monday\\|Tuesday\\|Wednesday\\|Thursday\\|Friday\\|"
142
+ "Saturday\\|Sunday\\)[\n ]+"
143
+ "\\([Tt]his\\|[Nn]ext\\)[ \n]+\\([Ww]eek\\)")
144
+ mhc-guess/make-date-from-english-relative-week 1 2 3)
145
+
146
+ throw
147
+
148
+ ("\\([0-90-9]+\\)[\n  ]*日"
149
+ mhc-guess/make-date-from-mmdd nil 1)
150
+
151
+ ("\\([0-90-9]+\\)[  ]*[((][月火水木金土日]"
152
+ mhc-guess/make-date-from-mmdd nil 1)
153
+
154
+ ("[^\((]\\([月火水木金土日]\\)\n?曜"
155
+ mhc-guess/make-date-from-relative-week nil 1)
156
+
157
+ (,(concat "\\(Monday\\|Tuesday\\|Wednesday\\|Thursday\\|Friday\\|"
158
+ "Saturday\\|Sunday\\)")
159
+ mhc-guess/make-date-from-english-relative-week 1 nil nil)
160
+
161
+ ("\\(本日\\|今日\\|あす\\|あした\\|あさって\\|明日\\|明後日\\)"
162
+ mhc-guess/make-date-from-relative-day 1)
163
+
164
+ (,(concat "\\([Tt]oday\\|[Tt]omorrow\\|"
165
+ "[Tt]he[ \n]+[Dd]ay[ \n]+[Aa]fter[ \n]+[Tt]omorrow\\)")
166
+ mhc-guess/make-date-from-english-relative-day 1)
167
+ ))
168
+
169
+ (defvar mhc-guess-time-regexp-list
170
+ `(
171
+ (,(concat "\\([0-90-9]+\\) *[時] *\\([0-90-9]+\\|半\\)?分?"
172
+ "\\([\n  ]*\\([〜−-]\\|から\\|より\\)[\n  午前後]*"
173
+ "\\([0-90-9]+\\) *[時]\\(間\\)? *\\([0-90-9]+\\|半\\)?\\)?")
174
+ mhc-guess/make-time-from-hhmm 1 2 5 7 6)
175
+ (,(concat "\\([0-90-9]+\\)[::]\\([0-90-9]+\\)"
176
+ "\\([\n  ]*\\([〜−-]\\|から\\|より\\)[\n  午前後]*"
177
+ "\\([0-90-9]+\\) *[::時]\\(間\\)? *\\([0-90-9]+\\|半\\)?\\)?")
178
+ mhc-guess/make-time-from-hhmm 1 2 5 7 6)
179
+ ))
180
+
181
+ (defvar mhc-guess-location-list '()
182
+ "*List of the regexps of the location, like this
183
+ '(\"第?[0-90-9〇-九]+応接室?\"
184
+ \"第?[0-90-9〇-九]+会議室[0-90-9〇-九]?\"))")
185
+
186
+ (defvar mhc-guess-location-regexp-list
187
+ `(
188
+ (,(concat "場[  ]*所[  ]*[::]*[\n  ]*\\([^\n  ]+\\)")
189
+ mhc-guess/make-location-from-string 1)
190
+ (,(concat "於[  ]*\\([^\n  ]+\\)")
191
+ mhc-guess/make-location-from-string 1)
192
+ (,(concat "[@@][  ]*\\([^\n  .]+\\)[  \n]")
193
+ mhc-guess/make-location-from-string 1)))
194
+
195
+ ;; keyword to score-alist:
196
+ ;; each element consists of (regexp relative-boundary sameline? score)
197
+ (defvar mhc-guess-keyword-score-alist
198
+ '(
199
+ ;; positive factor
200
+ ("^[\t ]+" -200 t +5)
201
+ ("次回" -200 nil +10)
202
+ ("\\(期間\\|月日\\|日程\\|時間帯\\|日時\\|開始時間\\)" -150 nil +5)
203
+ ("\\(期間\\|月日\\|日程\\|時間帯\\|日時\\|開始時間\\)[::]" -150 t +5)
204
+ ("\\(から\\|〜\\|変更\\|延期\\|順延\\|開始\\)" +80 nil +4)
205
+ ;; negative factor
206
+ ("\\(休み\\|除く\\|中止\\|までに\\)" +80 t -10)
207
+ ("出欠" -80 nil -5)
208
+ ("^\\(On\\|At\\|Date:\\) " -200 t -20)
209
+ ("\\(Jan\\|Feb\\|Mar\\|Apr\\|May\\|Jun\\)" -200 t -20)
210
+ ("\\(Jul\\|Aug\\|Sep\\|Oct\\|Nov\\|Dec\\)" -200 t -20)
211
+ ("^\\([ a-zA-Z]*>\\)+ *" -200 t -15)
212
+ ))
213
+
214
+ (defvar mhc-guess/location-regexp-list nil)
215
+
216
+ ;;
217
+ ;; manipulate guess-candidate structure.
218
+ ;;
219
+
220
+ (defmacro mhc-guess-get-date (obj) `(aref ,obj 0))
221
+ (defmacro mhc-guess-get-time (obj) `(aref ,obj 0))
222
+ (defmacro mhc-guess-get-date-or-time (obj) `(aref ,obj 0))
223
+
224
+ (defmacro mhc-guess-get-date-end (obj) `(aref ,obj 1))
225
+ (defmacro mhc-guess-get-time-end (obj) `(aref ,obj 1))
226
+ (defmacro mhc-guess-get-date-or-time-end (obj) `(aref ,obj 1))
227
+
228
+ (defmacro mhc-guess-get-begin (obj) `(aref ,obj 2))
229
+ (defmacro mhc-guess-get-end (obj) `(aref ,obj 3))
230
+ (defmacro mhc-guess-get-score (obj) `(aref ,obj 4))
231
+ (defmacro mhc-guess-get-debug (obj) `(aref ,obj 5))
232
+
233
+ (defmacro mhc-guess-set-date (obj val) `(aset ,obj 0 ,val))
234
+ (defmacro mhc-guess-set-time (obj val) `(aset ,obj 0 ,val))
235
+
236
+ (defmacro mhc-guess-set-date-end (obj val) `(aset ,obj 1 ,val))
237
+ (defmacro mhc-guess-set-time-end (obj val) `(aset ,obj 1 ,val))
238
+
239
+ (defmacro mhc-guess-set-begin (obj val) `(aset ,obj 2 ,val))
240
+ (defmacro mhc-guess-set-end (obj val) `(aset ,obj 3 ,val))
241
+ (defmacro mhc-guess-set-score (obj val) `(aset ,obj 4 ,val))
242
+ (defmacro mhc-guess-set-debug (obj val) `(aset ,obj 5 ,val))
243
+
244
+ (defun mhc-guess/new (&optional date-or-time date-or-time-end begin end score debug)
245
+ (vector date-or-time date-or-time-end begin end score debug))
246
+
247
+ ;;
248
+ ;; pulic entry
249
+ ;;
250
+
251
+ (defun mhc-guess-date (&optional hint1)
252
+ (let ((now (or (mhc-date-new-from-string3 (mhc-header-get-value "Date"))
253
+ (mhc-date-now))))
254
+ (mhc-guess/guess mhc-guess-date-regexp-list hint1 now)))
255
+
256
+ (defun mhc-guess-time (&optional hint1)
257
+ (mhc-guess/guess mhc-guess-time-regexp-list hint1))
258
+
259
+ (defun mhc-guess-location-setup ()
260
+ (if mhc-guess-location-list
261
+ (let ((list mhc-guess-location-list)
262
+ regex)
263
+ (while list
264
+ (setq regex (concat regex "\\(" (car list) "\\)"))
265
+ (setq list (cdr list))
266
+ (when list (setq regex (concat regex "\\|"))))
267
+ (setq mhc-guess/location-regexp-list
268
+ (cons `(,regex mhc-guess/make-location-from-string 0)
269
+ mhc-guess-location-regexp-list)))
270
+ (setq mhc-guess/location-regexp-list mhc-guess-location-regexp-list)))
271
+
272
+ (defun mhc-guess-location (&optional hint1)
273
+ (mhc-guess/guess mhc-guess/location-regexp-list hint1))
274
+
275
+ (defun mhc-guess/guess (control-regexp-lst &optional hint1 now)
276
+ (let ((score-list
277
+ (mhc-guess/score (mhc-guess/gather-candidate control-regexp-lst now)
278
+ mhc-guess-keyword-score-alist
279
+ hint1
280
+ now)))
281
+ (sort score-list
282
+ (function (lambda (a b)
283
+ (if (= (mhc-guess-get-score a) (mhc-guess-get-score b))
284
+ (< (- (mhc-guess-get-end b) (mhc-guess-get-begin b))
285
+ (- (mhc-guess-get-end a) (mhc-guess-get-begin a)))
286
+ (< (mhc-guess-get-score b)
287
+ (mhc-guess-get-score a))))))))
288
+ ;;
289
+ ;; gather date/time.
290
+ ;;
291
+
292
+ (defun mhc-guess/gather-candidate (control-regexp-lst &optional now)
293
+ (let ((ret nil) cand-lst)
294
+ (while control-regexp-lst
295
+ (cond
296
+ ((listp (car control-regexp-lst))
297
+ (if (setq cand-lst
298
+ (mhc-guess/gather-candidate2
299
+ (car (car control-regexp-lst)) ;; regexp
300
+ (car (cdr (car control-regexp-lst))) ;; convfunc
301
+ (cdr (cdr (car control-regexp-lst))) ;; posision list
302
+ now ;; current date
303
+ ))
304
+ (setq ret (nconc ret cand-lst))))
305
+ ((and (string= "throw" (symbol-name (car control-regexp-lst))) ret)
306
+ (setq control-regexp-lst nil)))
307
+ (setq control-regexp-lst (cdr control-regexp-lst)))
308
+ ret))
309
+
310
+ (defun mhc-guess/gather-candidate2 (regexp convfunc pos-list &optional now)
311
+ (let* (lst duration param-list p)
312
+ (save-excursion
313
+ ;; skip Header
314
+ (goto-char (point-min))
315
+ (re-search-forward "^-*$" nil t)
316
+ ;; search candities.
317
+ (while (re-search-forward regexp nil t)
318
+ (setq p pos-list
319
+ param-list nil)
320
+ (while p
321
+ (setq param-list
322
+ (cons
323
+ (if (and (car p) (match-beginning (car p)))
324
+ (buffer-substring (match-beginning (car p))
325
+ (match-end (car p)))
326
+ nil)
327
+ param-list))
328
+ (setq p (cdr p)))
329
+ (setq duration (apply 'funcall convfunc now (nreverse param-list)))
330
+ (if (car duration)
331
+ (setq lst
332
+ (cons
333
+ (mhc-guess/new (car duration)
334
+ (cdr duration)
335
+ (match-beginning 0)
336
+ (match-end 0)
337
+ nil
338
+ (format "%s with %s" convfunc regexp))
339
+ lst)))))
340
+ (nreverse lst)))
341
+
342
+ ;;
343
+ ;; make date from string.
344
+ ;;
345
+
346
+
347
+ (defun mhc-guess/make-date-from-yyyymmdd (now yy-str mm-str dd-str)
348
+ (let (date)
349
+ (if (setq date (mhc-date-new
350
+ (mhc-guess/string-to-int yy-str)
351
+ (mhc-guess/string-to-int mm-str)
352
+ (mhc-guess/string-to-int dd-str)
353
+ t)) ; noerror is t.
354
+ (cons date nil))))
355
+
356
+ (defun mhc-guess/make-date-from-mmdd
357
+ (now mm-str dd-str &optional mm-str2 dd-str2 relative)
358
+ (let* ((start nil) (end nil))
359
+ (setq start (mhc-guess/make-date-from-mmdd2 now mm-str dd-str))
360
+ (if start
361
+ (setq end (mhc-guess/make-date-from-mmdd2 start mm-str2 dd-str2)))
362
+ (cond
363
+ ((null start)
364
+ nil)
365
+ ((null end)
366
+ (cons start nil))
367
+ (relative
368
+ (cons start (mhc-date+ start end)))
369
+ (t
370
+ (cons start end)))))
371
+
372
+ (defun mhc-guess/make-date-from-mmdd2 (now mm-str dd-str)
373
+ (let ((data (match-data))
374
+ (mm (if mm-str (mhc-guess/string-to-int mm-str) 0))
375
+ (dd (if dd-str (mhc-guess/string-to-int dd-str) 0))
376
+ (year-offset 0)
377
+ date)
378
+ (cond
379
+ ((string= mm-str "来")
380
+ (setq mm (mhc-date-mm (mhc-date-mm++ now))))
381
+ ((string= mm-str "今")
382
+ (setq mm (mhc-date-mm now)))
383
+ ((= mm 0)
384
+ (setq mm (mhc-date-mm now))))
385
+ (if (not
386
+ (setq date
387
+ (mhc-date-new (mhc-date-yy now) mm dd t))) ;; noerror is t
388
+ ()
389
+ ;; if date is past, assume the next year.
390
+ (if (mhc-date< date now)
391
+ (setq year-offset (1+ year-offset)))
392
+ ;; if date is far future, assume the last year.
393
+ (if (< 300 (+ (mhc-date- date now) (* year-offset 365)))
394
+ (setq year-offset (1- year-offset)))
395
+ (setq date (mhc-date-yy+ date year-offset)))
396
+ (store-match-data data)
397
+ date))
398
+
399
+ (defun mhc-guess/make-date-from-usa-style-date (now month-str dd-str yy-str)
400
+ (if (and (null mhc-guess-ignore-english-date)
401
+ (memq 'usa mhc-guess-english-date-format))
402
+ (mhc-guess/make-date-from-english-date now month-str dd-str yy-str)))
403
+
404
+ (defun mhc-guess/make-date-from-british-style-date (now dd-str month-str yy-str)
405
+ (if (and (null mhc-guess-ignore-english-date)
406
+ (memq 'british mhc-guess-english-date-format))
407
+ (mhc-guess/make-date-from-english-date now month-str dd-str yy-str)))
408
+
409
+ (defun mhc-guess/make-date-from-english-date (now month-str dd-str yy-str)
410
+ (let* ((month-alist
411
+ '(("Jan" . "1") ("Feb" . "2") ("Mar" . "3") ("Apr" . "4")
412
+ ("May" . "5") ("Jun" . "6") ("Jul" . "7") ("Aug" . "8")
413
+ ("Sep" . "9") ("Oct" . "10") ("Nov" . "11") ("Dec" . "12")))
414
+ (mm-str (cdr (assoc (capitalize (substring month-str 0 3))
415
+ month-alist)))
416
+ (yy-length (length yy-str)))
417
+ (cond ((= yy-length 4) ; "yyyy"
418
+ (mhc-guess/make-date-from-yyyymmdd now yy-str mm-str dd-str))
419
+ ((or (= yy-length 3) (= yy-length 2)) ; "'yy" or "yy"
420
+ (mhc-guess/make-date-from-yyyymmdd
421
+ now
422
+ (concat (substring (format-time-string "%Y") 0 2)
423
+ (substring yy-str -2))
424
+ mm-str dd-str))
425
+ (t
426
+ (mhc-guess/make-date-from-mmdd now mm-str dd-str)))))
427
+
428
+ (defun mhc-guess/make-date-from-relative-day (now rel-word)
429
+ (cond
430
+ ((null rel-word)
431
+ nil)
432
+ ((or (string= rel-word "今日") (string= rel-word "本日"))
433
+ (cons now nil))
434
+ ((or (string= rel-word "あす")
435
+ (string= rel-word "あした")
436
+ (string= rel-word "明日"))
437
+ (cons (mhc-date++ now) nil))
438
+ ((or (string= rel-word "あさって")
439
+ (string= rel-word "明後日"))
440
+ (cons (mhc-date+ now 2) nil))))
441
+
442
+ (defun mhc-guess/make-date-from-english-relative-day (now rel-word)
443
+ (unless mhc-guess-ignore-english-date
444
+ (let ((rel (downcase rel-word)))
445
+ (cond
446
+ ((null rel)
447
+ nil)
448
+ ((string= rel "today")
449
+ (cons now nil))
450
+ ((string= rel "tomorrow")
451
+ (cons (mhc-date++ now) nil))
452
+ (t ;; the day after tommorow.
453
+ (cons (mhc-date+ now 2) nil))))))
454
+
455
+ (defun mhc-guess/make-date-from-relative-week (now rel-word week)
456
+ (let ((data (match-data))
457
+ (ww (string-match week "日月火水木金土"))
458
+ (date (or now (mhc-date-now)))
459
+ off)
460
+ (setq off (- ww (mhc-date-ww date)))
461
+ (if (string= week "日") (setq off (+ 7 off)))
462
+ (setq off
463
+ (cond
464
+ ((or (null rel-word)
465
+ (string= rel-word "今度")
466
+ (string= rel-word "次"))
467
+ (if (<= off 0) (+ 7 off) off))
468
+ ((string= rel-word "今週") off)
469
+ ((string= rel-word "来週")
470
+ (+ off 7))
471
+ ((string= rel-word "再来週")
472
+ (+ off 14))))
473
+ (store-match-data data)
474
+ (cons (mhc-date+ date off) nil)
475
+ ))
476
+
477
+ (defun mhc-guess/make-date-from-english-relative-week (now dow rel-word week)
478
+ (unless mhc-guess-ignore-english-date
479
+ (let ((dow-alist '(("Monday" . "月") ("Tuesday" . "火")
480
+ ("Wednesday" . "水") ("Thursday" . "木")
481
+ ("Friday" . "金") ("Saturday" . "土")
482
+ ("Sunday" . "日")))
483
+ (rel (when (stringp rel-word)
484
+ (downcase rel-word))))
485
+ (mhc-guess/make-date-from-relative-week
486
+ now
487
+ (if (null rel)
488
+ nil
489
+ (cond ((and (string= rel "this") (null week))
490
+ "今度")
491
+ ((and (string= rel "this") week)
492
+ "今週")
493
+ ((and (string= rel "next") (null week))
494
+ "今度")
495
+ ((and (string= rel "next") week)
496
+ "来週")
497
+ (t
498
+ nil)))
499
+ (cdr (assoc-string dow dow-alist t))))))
500
+
501
+ ;;
502
+ ;; make time from string.
503
+ ;;
504
+
505
+ (defun mhc-guess/make-time-from-hhmm
506
+ (now hh-str mm-str hh-str2 mm-str2 &optional relative)
507
+ (let ((start (mhc-guess/make-time-from-hhmm2 hh-str mm-str))
508
+ (end (mhc-guess/make-time-from-hhmm2 hh-str2 mm-str2 relative)))
509
+ (cond
510
+ ((null start)
511
+ nil)
512
+ ((null end)
513
+ (cons start nil))
514
+ (relative
515
+ (cons start (mhc-time+ start end)))
516
+ (t
517
+ (cons start end)))))
518
+
519
+ (defun mhc-guess/make-time-from-hhmm2 (hh-str mm-str &optional relative)
520
+ (let (xHH xMM)
521
+ (if (null hh-str)
522
+ nil ;; retun value
523
+
524
+ (setq xHH (mhc-guess/string-to-int hh-str))
525
+ (if (and (not relative) (< xHH 8)) ;; 8 depends on my life style.
526
+ (setq xHH (+ xHH 12)))
527
+ (setq xMM
528
+ (cond
529
+ ((not mm-str) 0)
530
+ ((string= mm-str "半") 30)
531
+ (t (mhc-guess/string-to-int mm-str))))
532
+ (mhc-time-new xHH xMM t))))
533
+
534
+ ;;
535
+ ;; make location from string
536
+ ;;
537
+
538
+ (defun mhc-guess/make-location-from-string (now str)
539
+ (cons str nil))
540
+
541
+ ;;
542
+ ;; scoring
543
+ ;;
544
+
545
+ (defun mhc-guess/score (candidate-lst score-alist &optional hint1 now)
546
+ (let ((clist candidate-lst)
547
+ total-score candidate regexp boundary sameline score slist)
548
+ (while clist
549
+ (setq candidate (car clist)
550
+ slist score-alist
551
+ total-score 0)
552
+
553
+ ;; set score using score-alist
554
+ (while slist
555
+ (setq regexp (nth 0 (car slist))
556
+ boundary (nth 1 (car slist))
557
+ sameline (nth 2 (car slist))
558
+ score (nth 3 (car slist)))
559
+ (if (mhc-guess/search-in-boundary
560
+ regexp
561
+ (mhc-guess-get-begin candidate)
562
+ boundary
563
+ sameline)
564
+ (setq total-score (+ total-score score)))
565
+ (setq slist (cdr slist)))
566
+
567
+ ;; hint1 is a position hint to encourage the near one.
568
+ (if (and hint1
569
+ (< hint1 (mhc-guess-get-begin candidate))
570
+ (< (- (mhc-guess-get-begin candidate) hint1) 100))
571
+ (setq total-score (+ total-score 10)))
572
+
573
+ ;; now is a date hint to discourage a past date.
574
+ (if (and now (mhc-date<= (mhc-guess-get-date candidate) now))
575
+ (setq total-score (- total-score 5)))
576
+
577
+ (mhc-guess-set-score candidate total-score)
578
+ (setq clist (cdr clist)))
579
+ candidate-lst))
580
+
581
+ (defun mhc-guess/search-in-boundary (regexp ptr rel-boundary sameline)
582
+ (let ((pmin (+ ptr rel-boundary)) (pmax (+ ptr rel-boundary)))
583
+ (save-excursion
584
+ (goto-char ptr)
585
+ (if sameline
586
+ (setq pmax (min pmax (save-excursion (end-of-line) (point)))
587
+ pmin (max pmin (save-excursion (beginning-of-line) (point)))))
588
+ (if (< 0 rel-boundary)
589
+ (and (< (point) pmax) (search-forward-regexp regexp pmax t))
590
+ (and (< pmin (point)) (search-backward-regexp regexp pmin t))))))
591
+
592
+ ;;
593
+ ;; string-to-int with code conversion.
594
+ ;;
595
+
596
+ (defconst mhc-guess/zenkaku-hankaku-alist
597
+ '(("0" . "0") ("1" . "1") ("2" . "2") ("3" . "3") ("4" . "4")
598
+ ("5" . "5") ("6" . "6") ("7" . "7") ("8" . "8") ("9" . "9")
599
+ ("/" . "/") (":" . ":")))
600
+
601
+ (defun mhc-guess/string-to-int (str)
602
+ (let ((chr "") (ret "") (data (match-data))
603
+ (z2h-alist
604
+ '(("0" . "0") ("1" . "1") ("2" . "2") ("3" . "3") ("4" . "4")
605
+ ("5" . "5") ("6" . "6") ("7" . "7") ("8" . "8") ("9" . "9")
606
+ ("/" . "/") (":" . ":"))))
607
+ (while (string-match "^." str)
608
+ (setq chr (substring str (match-beginning 0) (match-end 0)))
609
+ (setq ret (concat ret (or (cdr (assoc chr z2h-alist)) chr)))
610
+ (setq str (substring str (match-end 0))))
611
+ (store-match-data data)
612
+ (string-to-number ret)))
613
+
614
+
615
+ ;;; Copyright Notice:
616
+
617
+ ;; Copyright (C) 1999, 2000 Yoshinari Nomura. All rights reserved.
618
+ ;; Copyright (C) 2000 MHC developing team. All rights reserved.
619
+
620
+ ;; Redistribution and use in source and binary forms, with or without
621
+ ;; modification, are permitted provided that the following conditions
622
+ ;; are met:
623
+ ;;
624
+ ;; 1. Redistributions of source code must retain the above copyright
625
+ ;; notice, this list of conditions and the following disclaimer.
626
+ ;; 2. Redistributions in binary form must reproduce the above copyright
627
+ ;; notice, this list of conditions and the following disclaimer in the
628
+ ;; documentation and/or other materials provided with the distribution.
629
+ ;; 3. Neither the name of the team nor the names of its contributors
630
+ ;; may be used to endorse or promote products derived from this software
631
+ ;; without specific prior written permission.
632
+ ;;
633
+ ;; THIS SOFTWARE IS PROVIDED BY THE TEAM AND CONTRIBUTORS ``AS IS''
634
+ ;; AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
635
+ ;; LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
636
+ ;; FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
637
+ ;; THE TEAM OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
638
+ ;; INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
639
+ ;; (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
640
+ ;; SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
641
+ ;; HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
642
+ ;; STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
643
+ ;; ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
644
+ ;; OF THE POSSIBILITY OF SUCH DAMAGE.
645
+
646
+ ;;; mhc-guess.el ends here
647
+
648
+