* url-util.el (url-insert-entities-in-string):
[bpt/emacs.git] / lisp / calendar / cal-hebrew.el
CommitLineData
3afbc435 1;;; cal-hebrew.el --- calendar functions for the Hebrew calendar
4b112ac4 2
0d1bb2ff 3;; Copyright (C) 1995, 1997, 2001, 2002, 2003, 2004, 2005, 2006, 2007,
ae940284 4;; 2008, 2009 Free Software Foundation, Inc.
4b112ac4 5
85d0ba86 6;; Author: Nachum Dershowitz <nachum@cs.uiuc.edu>
6b789b4b 7;; Edward M. Reingold <reingold@cs.uiuc.edu>
dbfca9c4 8;; Maintainer: Glenn Morris <rgm@gnu.org>
4b112ac4
ER
9;; Keywords: calendar
10;; Human-Keywords: Hebrew calendar, calendar, diary
11
12;; This file is part of GNU Emacs.
13
2ed66575 14;; GNU Emacs is free software: you can redistribute it and/or modify
4b112ac4 15;; it under the terms of the GNU General Public License as published by
2ed66575
GM
16;; the Free Software Foundation, either version 3 of the License, or
17;; (at your option) any later version.
4b112ac4
ER
18
19;; GNU Emacs is distributed in the hope that it will be useful,
20;; but WITHOUT ANY WARRANTY; without even the implied warranty of
21;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22;; GNU General Public License for more details.
23
24;; You should have received a copy of the GNU General Public License
2ed66575 25;; along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>.
4b112ac4
ER
26
27;;; Commentary:
28
618c03c1 29;; See calendar.el.
a96a5fca 30
4b112ac4
ER
31;;; Code:
32
da3fc020 33(require 'calendar)
4b112ac4 34
1a9f2b77
GM
35(define-obsolete-variable-alias 'diary-sabbath-candles-minutes
36 'diary-hebrew-sabbath-candles-minutes "23.1")
37
87e1e9cd
GM
38(defcustom diary-hebrew-sabbath-candles-minutes 18
39 "Number of minutes before sunset for sabbath candle lighting.
40Used by `diary-hebrew-sabbath-candles'."
41 :group 'diary
42 :type 'integer
43 :version "21.1")
44
87e1e9cd
GM
45;; End of user options.
46
8fc9e5a0 47(defun calendar-hebrew-leap-year-p (year)
6afe7cdd 48 "Non-nil if YEAR is a Hebrew calendar leap year."
4b112ac4
ER
49 (< (% (1+ (* 7 year)) 19) 7))
50
8fc9e5a0 51(defun calendar-hebrew-last-month-of-year (year)
4b112ac4 52 "The last month of the Hebrew calendar YEAR."
8fc9e5a0 53 (if (calendar-hebrew-leap-year-p year)
4b112ac4
ER
54 13
55 12))
56
8fc9e5a0 57(defun calendar-hebrew-elapsed-days (year)
6b789b4b
GM
58 "Days to mean conjunction of Tishri of Hebrew YEAR.
59Measured from Sunday before start of Hebrew calendar."
4b112ac4 60 (let* ((months-elapsed
9c68082d
GM
61 (+ (* 235 (/ (1- year) 19)) ; months in complete cycles so far
62 (* 12 (% (1- year) 19)) ; regular months in this cycle
63 (/ (1+ (* 7 (% (1- year) 19))) 19))) ; leap months this cycle
4b112ac4
ER
64 (parts-elapsed (+ 204 (* 793 (% months-elapsed 1080))))
65 (hours-elapsed (+ 5
66 (* 12 months-elapsed)
67 (* 793 (/ months-elapsed 1080))
68 (/ parts-elapsed 1080)))
71ea27ee 69 (parts ; conjunction parts
4b112ac4 70 (+ (* 1080 (% hours-elapsed 24)) (% parts-elapsed 1080)))
71ea27ee 71 (day ; conjunction day
4b112ac4
ER
72 (+ 1 (* 29 months-elapsed) (/ hours-elapsed 24)))
73 (alternative-day
9c68082d 74 (if (or (>= parts 19440) ; if the new moon is at or after midday
71ea27ee 75 (and (= (% day 7) 2) ; ...or is on a Tuesday...
9c68082d 76 (>= parts 9924) ; at 9 hours, 204 parts or later...
71ea27ee 77 ;; of a common year...
8fc9e5a0 78 (not (calendar-hebrew-leap-year-p year)))
71ea27ee 79 (and (= (% day 7) 1) ; ...or is on a Monday...
9c68082d 80 (>= parts 16789) ; at 15 hours, 589 parts or later...
71ea27ee 81 ;; at the end of a leap year.
8fc9e5a0 82 (calendar-hebrew-leap-year-p (1- year))))
71ea27ee 83 ;; Then postpone Rosh HaShanah one day.
4b112ac4 84 (1+ day)
71ea27ee 85 ;; Else:
4b112ac4 86 day)))
9c68082d
GM
87 ;; If Rosh HaShanah would occur on Sunday, Wednesday, or Friday
88 (if (memq (% alternative-day 7) (list 0 3 5))
71ea27ee 89 ;; Then postpone it one (more) day and return.
4b112ac4 90 (1+ alternative-day)
9c68082d 91 ;; Else return.
4b112ac4
ER
92 alternative-day)))
93
8fc9e5a0 94(defun calendar-hebrew-days-in-year (year)
4b112ac4 95 "Number of days in Hebrew YEAR."
8fc9e5a0
GM
96 (- (calendar-hebrew-elapsed-days (1+ year))
97 (calendar-hebrew-elapsed-days year)))
4b112ac4 98
8fc9e5a0 99(defun calendar-hebrew-long-heshvan-p (year)
6afe7cdd 100 "Non-nil if Heshvan is long in Hebrew YEAR."
8fc9e5a0 101 (= (% (calendar-hebrew-days-in-year year) 10) 5))
4b112ac4 102
8fc9e5a0 103(defun calendar-hebrew-short-kislev-p (year)
6afe7cdd 104 "Non-nil if Kislev is short in Hebrew YEAR."
8fc9e5a0 105 (= (% (calendar-hebrew-days-in-year year) 10) 3))
4b112ac4 106
8fc9e5a0 107(defun calendar-hebrew-last-day-of-month (month year)
da3fc020
GM
108 "The last day of MONTH in YEAR."
109 (if (or (memq month (list 2 4 6 10 13))
8fc9e5a0
GM
110 (and (= month 12) (not (calendar-hebrew-leap-year-p year)))
111 (and (= month 8) (not (calendar-hebrew-long-heshvan-p year)))
112 (and (= month 9) (calendar-hebrew-short-kislev-p year)))
da3fc020
GM
113 29
114 30))
115
8fc9e5a0 116(defun calendar-hebrew-to-absolute (date)
4b112ac4
ER
117 "Absolute date of Hebrew DATE.
118The absolute date is the number of days elapsed since the (imaginary)
119Gregorian date Sunday, December 31, 1 BC."
e803eab7
GM
120 (let ((month (calendar-extract-month date))
121 (day (calendar-extract-day date))
122 (year (calendar-extract-year date)))
71ea27ee
GM
123 (+ day ; days so far this month
124 (if (< month 7) ; before Tishri
125 ;; Then add days in prior months this year before and after Nisan.
4b112ac4 126 (+ (calendar-sum
8fc9e5a0
GM
127 m 7 (<= m (calendar-hebrew-last-month-of-year year))
128 (calendar-hebrew-last-day-of-month m year))
4b112ac4
ER
129 (calendar-sum
130 m 1 (< m month)
8fc9e5a0 131 (calendar-hebrew-last-day-of-month m year)))
71ea27ee 132 ;; Else add days in prior months this year.
4b112ac4
ER
133 (calendar-sum
134 m 7 (< m month)
8fc9e5a0
GM
135 (calendar-hebrew-last-day-of-month m year)))
136 (calendar-hebrew-elapsed-days year) ; days in prior years
71ea27ee 137 -1373429))) ; days elapsed before absolute date 1
4b112ac4 138
8fc9e5a0
GM
139(define-obsolete-function-alias 'calendar-absolute-from-hebrew
140 'calendar-hebrew-to-absolute "23.1")
141
da3fc020
GM
142(defun calendar-hebrew-from-absolute (date)
143 "Compute the Hebrew date (month day year) corresponding to absolute DATE.
144The absolute date is the number of days elapsed since the (imaginary)
145Gregorian date Sunday, December 31, 1 BC."
146 (let* ((greg-date (calendar-gregorian-from-absolute date))
e803eab7 147 (year (+ 3760 (calendar-extract-year greg-date)))
da3fc020 148 (month (aref [9 10 11 12 1 2 3 4 7 7 7 8]
e803eab7 149 (1- (calendar-extract-month greg-date))))
6b789b4b 150 (length (progn
8fc9e5a0 151 (while (>= date (calendar-hebrew-to-absolute
6b789b4b
GM
152 (list 7 1 (1+ year))))
153 (setq year (1+ year)))
8fc9e5a0 154 (calendar-hebrew-last-month-of-year year)))
28c02796 155 day)
6b789b4b 156 (while (> date
8fc9e5a0 157 (calendar-hebrew-to-absolute
6b789b4b 158 (list month
8fc9e5a0 159 (calendar-hebrew-last-day-of-month month year)
6b789b4b
GM
160 year)))
161 (setq month (1+ (% month length))))
da3fc020 162 (setq day (1+
8fc9e5a0 163 (- date (calendar-hebrew-to-absolute (list month 1 year)))))
da3fc020
GM
164 (list month day year)))
165
711d00e7 166(defconst calendar-hebrew-month-name-array-common-year
4b112ac4 167 ["Nisan" "Iyar" "Sivan" "Tammuz" "Av" "Elul" "Tishri"
da3fc020 168 "Heshvan" "Kislev" "Teveth" "Shevat" "Adar"]
71ea27ee 169 "Array of strings giving the names of the Hebrew months in a common year.")
4b112ac4 170
711d00e7 171(defconst calendar-hebrew-month-name-array-leap-year
4b112ac4 172 ["Nisan" "Iyar" "Sivan" "Tammuz" "Av" "Elul" "Tishri"
da3fc020 173 "Heshvan" "Kislev" "Teveth" "Shevat" "Adar I" "Adar II"]
71ea27ee 174 "Array of strings giving the names of the Hebrew months in a leap year.")
4b112ac4 175
28b3c0f5 176;;;###cal-autoload
4b112ac4
ER
177(defun calendar-hebrew-date-string (&optional date)
178 "String of Hebrew date before sunset of Gregorian DATE.
179Defaults to today's date if DATE is not given.
180Driven by the variable `calendar-date-display-form'."
181 (let* ((hebrew-date (calendar-hebrew-from-absolute
182 (calendar-absolute-from-gregorian
183 (or date (calendar-current-date)))))
184 (calendar-month-name-array
e803eab7 185 (if (calendar-hebrew-leap-year-p (calendar-extract-year hebrew-date))
4b112ac4
ER
186 calendar-hebrew-month-name-array-leap-year
187 calendar-hebrew-month-name-array-common-year)))
188 (calendar-date-string hebrew-date nil t)))
189
28b3c0f5 190;;;###cal-autoload
8fc9e5a0 191(defun calendar-hebrew-print-date ()
4b112ac4
ER
192 "Show the Hebrew calendar equivalent of the date under the cursor."
193 (interactive)
194 (message "Hebrew date (until sunset): %s"
195 (calendar-hebrew-date-string (calendar-cursor-to-date t))))
196
8fc9e5a0
GM
197(define-obsolete-function-alias 'calendar-print-hebrew-date
198 'calendar-hebrew-print-date "23.1")
199
200(defun calendar-hebrew-yahrzeit (death-date year)
4b112ac4 201 "Absolute date of the anniversary of Hebrew DEATH-DATE in Hebrew YEAR."
e803eab7
GM
202 (let ((death-day (calendar-extract-day death-date))
203 (death-month (calendar-extract-month death-date))
204 (death-year (calendar-extract-year death-date)))
4b112ac4
ER
205 (cond
206 ;; If it's Heshvan 30 it depends on the first anniversary; if
207 ;; that was not Heshvan 30, use the day before Kislev 1.
208 ((and (= death-month 8)
209 (= death-day 30)
8fc9e5a0
GM
210 (not (calendar-hebrew-long-heshvan-p (1+ death-year))))
211 (1- (calendar-hebrew-to-absolute (list 9 1 year))))
9c68082d
GM
212 ;; If it's Kislev 30 it depends on the first anniversary; if that
213 ;; was not Kislev 30, use the day before Teveth 1.
4b112ac4
ER
214 ((and (= death-month 9)
215 (= death-day 30)
8fc9e5a0
GM
216 (calendar-hebrew-short-kislev-p (1+ death-year)))
217 (1- (calendar-hebrew-to-absolute (list 10 1 year))))
9c68082d
GM
218 ;; If it's Adar II, use the same day in last month of year (Adar
219 ;; or Adar II).
4b112ac4 220 ((= death-month 13)
8fc9e5a0
GM
221 (calendar-hebrew-to-absolute
222 (list (calendar-hebrew-last-month-of-year year) death-day year)))
9c68082d
GM
223 ;; If it's the 30th in Adar I and year is not a leap year (so
224 ;; Adar has only 29 days), use the last day in Shevat.
4b112ac4
ER
225 ((and (= death-day 30)
226 (= death-month 12)
8fc9e5a0
GM
227 (not (calendar-hebrew-leap-year-p year)))
228 (calendar-hebrew-to-absolute (list 11 30 year)))
4b112ac4 229 ;; In all other cases, use the normal anniversary of the date of death.
8fc9e5a0 230 (t (calendar-hebrew-to-absolute
4b112ac4
ER
231 (list death-month death-day year))))))
232
8fc9e5a0
GM
233(define-obsolete-function-alias 'hebrew-calendar-yahrzeit
234 'calendar-hebrew-yahrzeit "23.1")
235
42281b7b
GM
236(defun calendar-hebrew-read-date ()
237 "Interactively read the arguments for a Hebrew date command.
238Reads a year, month, and day."
28c02796
GM
239 (let* ((today (calendar-current-date))
240 (year (calendar-read
241 "Hebrew calendar year (>3760): "
242 (lambda (x) (> x 3760))
d92bcf94 243 (number-to-string
e803eab7 244 (calendar-extract-year
28c02796
GM
245 (calendar-hebrew-from-absolute
246 (calendar-absolute-from-gregorian today))))))
8fc9e5a0 247 (month-array (if (calendar-hebrew-leap-year-p year)
28c02796
GM
248 calendar-hebrew-month-name-array-leap-year
249 calendar-hebrew-month-name-array-common-year))
250 (completion-ignore-case t)
251 (month (cdr (assoc-string
252 (completing-read
253 "Hebrew calendar month name: "
254 (mapcar 'list (append month-array nil))
255 (if (= year 3761)
256 (lambda (x)
257 (let ((m (cdr
258 (assoc-string
259 (car x)
260 (calendar-make-alist month-array)
261 t))))
262 (< 0
8fc9e5a0 263 (calendar-hebrew-to-absolute
28c02796 264 (list m
8fc9e5a0 265 (calendar-hebrew-last-day-of-month
28c02796
GM
266 m year)
267 year))))))
268 t)
269 (calendar-make-alist month-array 1) t)))
8fc9e5a0 270 (last (calendar-hebrew-last-day-of-month month year))
28c02796
GM
271 (first (if (and (= year 3761) (= month 10))
272 18 1))
273 (day (calendar-read
274 (format "Hebrew calendar day (%d-%d): "
275 first last)
276 (lambda (x) (and (<= first x) (<= x last))))))
277 (list (list month day year))))
278
28b3c0f5 279;;;###cal-autoload
8fc9e5a0 280(defun calendar-hebrew-goto-date (date &optional noecho)
8f11970d 281 "Move cursor to Hebrew DATE; echo Hebrew date unless NOECHO is non-nil."
42281b7b 282 (interactive (calendar-hebrew-read-date))
4b112ac4 283 (calendar-goto-date (calendar-gregorian-from-absolute
8fc9e5a0
GM
284 (calendar-hebrew-to-absolute date)))
285 (or noecho (calendar-hebrew-print-date)))
286
287(define-obsolete-function-alias 'calendar-goto-hebrew-date
288 'calendar-hebrew-goto-date "23.1")
4b112ac4 289
e803eab7 290(defvar displayed-month) ; from calendar-generate
8f11970d 291
6b789b4b
GM
292(defun calendar-hebrew-date-is-visible-p (month day)
293 "Return non-nil if Hebrew MONTH DAY is visible in the calendar window.
294Returns the corresponding Gregorian date."
9c68082d
GM
295 ;; This test is only to speed things up a bit; it works fine without it.
296 (if (memq displayed-month
1d2a9d53
GM
297 ;; What this is doing is equivalent to +1,2,3,4,5 modulo 12, ie:
298 ;; (mapcar (lambda (n) (let ((x (mod n 12)))
299 ;; (if (zerop x) 12
300 ;; x)))
301 ;; (number-sequence (1+ month) (+ 5 month)))
302 ;; Ie it makes a list:
303 ;; 2 3 4 5 6 when month = 1
304 ;; 3 4 5 6 7 when month = 2
305 ;; ...
306 ;; 8 9 10 11 12 when month = 7
307 ;; 9 10 11 12 1 when month = 8
308 ;; ...
309 ;; 12 1 2 3 4 when month = 11
310 ;; 1 2 3 4 5 when month = 12
311 ;; This implies that hebrew month N cannot occur outside
312 ;; Gregorian months N:N+6 (the calendar shows
313 ;; displayed-month +/- 1 at any time).
314 ;; So to put it another way:
315 ;; (calendar-interval month 1 displayed-month
316 ;; (if (> month displayed-month) 2 1))
317 ;; must be >= 1 and <= 5. This could be expanded to:
318 ;; (if (> month displayed-month) (+ 12 (- displayed-month month))
319 ;; (- displayed-month month)
9c68082d 320 (list
4b112ac4
ER
321 (if (< 11 month) (- month 11) (+ month 1))
322 (if (< 10 month) (- month 10) (+ month 2))
323 (if (< 9 month) (- month 9) (+ month 3))
324 (if (< 8 month) (- month 8) (+ month 4))
325 (if (< 7 month) (- month 7) (+ month 5))))
2f264ff6 326 (calendar-nongregorian-visible-p
8fc9e5a0 327 month day 'calendar-hebrew-to-absolute
2f264ff6
GM
328 'calendar-hebrew-from-absolute
329 ;; Hebrew new year is start of month 7.
330 ;; If hmonth >= 7, choose the higher year.
331 (lambda (m) (> m 6)))))
6b789b4b
GM
332
333;;;###holiday-autoload
334(defun holiday-hebrew (month day string)
335 "Holiday on MONTH, DAY (Hebrew) called STRING.
336If MONTH, DAY (Hebrew) is visible, the value returned is corresponding
337Gregorian date in the form of the list (((month day year) STRING)). Returns
338nil if it is not visible in the current calendar window."
339 (let ((gdate (calendar-hebrew-date-is-visible-p month day)))
340 (if gdate (list (list gdate string)))))
4b112ac4 341
e475d400
GM
342;; h-r-h-e should be called from holidays code.
343(declare-function holiday-filter-visible-calendar "holidays" (l))
344
2f264ff6
GM
345(defvar displayed-year)
346
28b3c0f5 347;;;###holiday-autoload
8fc9e5a0 348(defun holiday-hebrew-rosh-hashanah (&optional all)
f2268dc0 349 "List of dates related to Rosh Hashanah, as visible in calendar window.
1c76c939 350Shows only the major holidays, unless `calendar-hebrew-all-holidays-flag'
f2268dc0
GM
351or ALL is non-nil."
352 (when (memq displayed-month '(8 9 10 11))
8fc9e5a0 353 (let ((abs-r-h (calendar-hebrew-to-absolute
f2268dc0
GM
354 (list 7 1 (+ displayed-year 3761)))))
355 (holiday-filter-visible-calendar
356 (append
357 (list
358 (list (calendar-gregorian-from-absolute abs-r-h)
359 (format "Rosh HaShanah %d" (+ 3761 displayed-year)))
360 (list (calendar-gregorian-from-absolute (+ abs-r-h 9))
361 "Yom Kippur")
362 (list (calendar-gregorian-from-absolute (+ abs-r-h 14))
363 "Sukkot")
364 (list (calendar-gregorian-from-absolute (+ abs-r-h 21))
365 "Shemini Atzeret")
366 (list (calendar-gregorian-from-absolute (+ abs-r-h 22))
367 "Simchat Torah"))
1c76c939 368 (when (or all calendar-hebrew-all-holidays-flag)
f2268dc0
GM
369 (list
370 (list (calendar-gregorian-from-absolute
371 (calendar-dayname-on-or-before 6 (- abs-r-h 4)))
372 "Selichot (night)")
373 (list (calendar-gregorian-from-absolute (1- abs-r-h))
374 "Erev Rosh HaShanah")
375 (list (calendar-gregorian-from-absolute (1+ abs-r-h))
376 "Rosh HaShanah (second day)")
377 (list (calendar-gregorian-from-absolute
378 (if (= (% abs-r-h 7) 4) (+ abs-r-h 3) (+ abs-r-h 2)))
379 "Tzom Gedaliah")
380 (list (calendar-gregorian-from-absolute
381 (calendar-dayname-on-or-before 6 (+ 7 abs-r-h)))
382 "Shabbat Shuvah")
383 (list (calendar-gregorian-from-absolute (+ abs-r-h 8))
384 "Erev Yom Kippur")
385 (list (calendar-gregorian-from-absolute (+ abs-r-h 13))
386 "Erev Sukkot")
387 (list (calendar-gregorian-from-absolute (+ abs-r-h 15))
388 "Sukkot (second day)")
389 (list (calendar-gregorian-from-absolute (+ abs-r-h 16))
390 "Hol Hamoed Sukkot (first day)")
391 (list (calendar-gregorian-from-absolute (+ abs-r-h 17))
392 "Hol Hamoed Sukkot (second day)")
393 (list (calendar-gregorian-from-absolute (+ abs-r-h 18))
394 "Hol Hamoed Sukkot (third day)")
395 (list (calendar-gregorian-from-absolute (+ abs-r-h 19))
396 "Hol Hamoed Sukkot (fourth day)")
397 (list (calendar-gregorian-from-absolute (+ abs-r-h 20))
398 "Hoshanah Rabbah"))))))))
4b112ac4 399
28b3c0f5 400;;;###holiday-autoload
8fc9e5a0
GM
401(define-obsolete-function-alias 'holiday-rosh-hashanah-etc
402 'holiday-hebrew-rosh-hashanah "23.1")
403
404;;;###holiday-autoload
405(defun holiday-hebrew-hanukkah (&optional all)
f2268dc0 406 "List of dates related to Hanukkah, as visible in calendar window.
1c76c939 407Shows only Hanukkah, unless `calendar-hebrew-all-holidays-flag' or ALL
f2268dc0 408is non-nil."
9c68082d 409 ;; This test is only to speed things up a bit, it works fine without it.
f2268dc0
GM
410 (when (memq displayed-month '(10 11 12 1 2))
411 (let* ((m displayed-month)
412 (y displayed-year)
413 (h-y (progn
e803eab7
GM
414 (calendar-increment-month m y 1)
415 (calendar-extract-year
f2268dc0
GM
416 (calendar-hebrew-from-absolute
417 (calendar-absolute-from-gregorian
418 (list m (calendar-last-day-of-month m y) y))))))
8fc9e5a0 419 (abs-h (calendar-hebrew-to-absolute (list 9 25 h-y)))
f2268dc0
GM
420 (ord ["first" "second" "third" "fourth" "fifth" "sixth"
421 "seventh" "eighth"])
422 han)
423 (holiday-filter-visible-calendar
1c76c939 424 (if (or all calendar-hebrew-all-holidays-flag)
f2268dc0
GM
425 (append
426 (list
427 (list (calendar-gregorian-from-absolute (1- abs-h))
428 "Erev Hanukkah"))
429 (dotimes (i 8 (nreverse han))
430 (push (list
431 (calendar-gregorian-from-absolute (+ abs-h i))
432 (format "Hanukkah (%s day)" (aref ord i)))
433 han)))
434 (list (list (calendar-gregorian-from-absolute abs-h) "Hanukkah")))))))
4b112ac4 435
28b3c0f5 436;;;###holiday-autoload
8fc9e5a0
GM
437(define-obsolete-function-alias 'holiday-hanukkah
438 'holiday-hebrew-hanukkah "23.1")
439
440;;;###holiday-autoload
441(defun holiday-hebrew-passover (&optional all)
f2268dc0 442 "List of dates related to Passover, as visible in calendar window.
1c76c939 443Shows only the major holidays, unless `calendar-hebrew-all-holidays-flag'
f2268dc0
GM
444or ALL is non-nil."
445 (when (< displayed-month 8)
8fc9e5a0 446 (let ((abs-p (calendar-hebrew-to-absolute
f2268dc0
GM
447 (list 1 15 (+ displayed-year 3760)))))
448 (holiday-filter-visible-calendar
449 ;; The first two are out of order when the others are added.
450 (append
451 (list
452 (list (calendar-gregorian-from-absolute abs-p) "Passover")
453 (list (calendar-gregorian-from-absolute (+ abs-p 50))
454 "Shavuot"))
1c76c939 455 (when (or all calendar-hebrew-all-holidays-flag)
f2268dc0
GM
456 (list
457 (list (calendar-gregorian-from-absolute
458 (calendar-dayname-on-or-before 6 (- abs-p 43)))
459 "Shabbat Shekalim")
460 (list (calendar-gregorian-from-absolute
461 (calendar-dayname-on-or-before 6 (- abs-p 30)))
462 "Shabbat Zachor")
463 (list (calendar-gregorian-from-absolute
464 (if (= (% abs-p 7) 2) (- abs-p 33) (- abs-p 31)))
465 "Fast of Esther")
466 (list (calendar-gregorian-from-absolute (- abs-p 31))
467 "Erev Purim")
468 (list (calendar-gregorian-from-absolute (- abs-p 30))
469 "Purim")
470 (list (calendar-gregorian-from-absolute
471 (if (zerop (% abs-p 7)) (- abs-p 28) (- abs-p 29)))
472 "Shushan Purim")
473 (list (calendar-gregorian-from-absolute
474 (- (calendar-dayname-on-or-before 6 (- abs-p 14)) 7))
475 "Shabbat Parah")
476 (list (calendar-gregorian-from-absolute
477 (calendar-dayname-on-or-before 6 (- abs-p 14)))
478 "Shabbat HaHodesh")
479 (list (calendar-gregorian-from-absolute
480 (calendar-dayname-on-or-before 6 (1- abs-p)))
481 "Shabbat HaGadol")
482 (list (calendar-gregorian-from-absolute (1- abs-p))
483 "Erev Passover")
484 (list (calendar-gregorian-from-absolute (1+ abs-p))
485 "Passover (second day)")
486 (list (calendar-gregorian-from-absolute (+ abs-p 2))
487 "Hol Hamoed Passover (first day)")
488 (list (calendar-gregorian-from-absolute (+ abs-p 3))
489 "Hol Hamoed Passover (second day)")
490 (list (calendar-gregorian-from-absolute (+ abs-p 4))
491 "Hol Hamoed Passover (third day)")
492 (list (calendar-gregorian-from-absolute (+ abs-p 5))
493 "Hol Hamoed Passover (fourth day)")
494 (list (calendar-gregorian-from-absolute (+ abs-p 6))
495 "Passover (seventh day)")
496 (list (calendar-gregorian-from-absolute (+ abs-p 7))
497 "Passover (eighth day)")
498 (list (calendar-gregorian-from-absolute
499 (if (zerop (% (+ abs-p 12) 7))
500 (+ abs-p 13)
501 (+ abs-p 12)))
502 "Yom HaShoah")
503 (list (calendar-gregorian-from-absolute
504 (if (zerop (% abs-p 7))
505 (+ abs-p 18)
506 (if (= (% abs-p 7) 6)
507 (+ abs-p 19)
508 (+ abs-p 20))))
509 "Yom HaAtzma'ut")
510 (list (calendar-gregorian-from-absolute (+ abs-p 33))
511 "Lag BaOmer")
512 (list (calendar-gregorian-from-absolute (+ abs-p 43))
513 "Yom Yerushalaim")
514 (list (calendar-gregorian-from-absolute (+ abs-p 49))
515 "Erev Shavuot")
516 (list (calendar-gregorian-from-absolute (+ abs-p 51))
517 "Shavuot (second day)"))))))))
4b112ac4 518
28b3c0f5 519;;;###holiday-autoload
8fc9e5a0
GM
520(define-obsolete-function-alias 'holiday-passover-etc
521 'holiday-hebrew-passover "23.1")
522
523;;;###holiday-autoload
524(defun holiday-hebrew-tisha-b-av ()
4b112ac4 525 "List of dates around Tisha B'Av, as visible in calendar window."
f2268dc0 526 (when (memq displayed-month '(5 6 7 8 9))
8fc9e5a0 527 (let ((abs-t-a (calendar-hebrew-to-absolute
28c02796 528 (list 5 9 (+ displayed-year 3760)))))
8705f7f3 529 (holiday-filter-visible-calendar
a1506d29 530 (list
4b112ac4
ER
531 (list (calendar-gregorian-from-absolute
532 (if (= (% abs-t-a 7) 6) (- abs-t-a 20) (- abs-t-a 21)))
533 "Tzom Tammuz")
534 (list (calendar-gregorian-from-absolute
535 (calendar-dayname-on-or-before 6 abs-t-a))
536 "Shabbat Hazon")
537 (list (calendar-gregorian-from-absolute
538 (if (= (% abs-t-a 7) 6) (1+ abs-t-a) abs-t-a))
539 "Tisha B'Av")
540 (list (calendar-gregorian-from-absolute
541 (calendar-dayname-on-or-before 6 (+ abs-t-a 7)))
542 "Shabbat Nahamu"))))))
543
8fc9e5a0
GM
544;;;###holiday-autoload
545(define-obsolete-function-alias 'holiday-tisha-b-av-etc
546 'holiday-hebrew-tisha-b-av "23.1")
547
f2268dc0
GM
548(autoload 'holiday-julian "cal-julian")
549
550;;;###holiday-autoload
551(defun holiday-hebrew-misc ()
552 "Miscellaneous Hebrew holidays, if visible in calendar window.
553Includes: Tal Umatar, Tzom Teveth, Tu B'Shevat, Shabbat Shirah, and
554Kiddush HaHamah."
555 (let ((m displayed-month)
556 (y displayed-year)
557 year h-year s-s)
558 (append
559 (holiday-julian
560 11
561 (progn
e803eab7
GM
562 (calendar-increment-month m y -1)
563 (setq year (calendar-extract-year
f2268dc0
GM
564 (calendar-julian-from-absolute
565 (calendar-absolute-from-gregorian (list m 1 y)))))
566 (if (zerop (% (1+ year) 4))
567 22
568 21)) "\"Tal Umatar\" (evening)")
569 (holiday-hebrew
570 10
571 (progn
e803eab7 572 (setq h-year (calendar-extract-year
f2268dc0
GM
573 (calendar-hebrew-from-absolute
574 (calendar-absolute-from-gregorian
575 (list displayed-month 28 displayed-year)))))
8fc9e5a0 576 (if (= 6 (% (calendar-hebrew-to-absolute (list 10 10 h-year))
f2268dc0
GM
577 7))
578 11 10))
579 "Tzom Teveth")
580 (holiday-hebrew 11 15 "Tu B'Shevat")
581 (holiday-hebrew
582 11
583 (progn
584 (setq m displayed-month
585 y displayed-year
586 h-year (progn
e803eab7
GM
587 (calendar-increment-month m y 1)
588 (calendar-extract-year
f2268dc0
GM
589 (calendar-hebrew-from-absolute
590 (calendar-absolute-from-gregorian
591 (list m (calendar-last-day-of-month m y) y)))))
592 s-s
593 (calendar-hebrew-from-absolute
594 (if (= 6
8fc9e5a0 595 (% (calendar-hebrew-to-absolute
f2268dc0
GM
596 (list 7 1 h-year))
597 7))
598 (calendar-dayname-on-or-before
8fc9e5a0 599 6 (calendar-hebrew-to-absolute
f2268dc0
GM
600 (list 11 17 h-year)))
601 (calendar-dayname-on-or-before
8fc9e5a0 602 6 (calendar-hebrew-to-absolute
f2268dc0 603 (list 11 16 h-year))))))
e803eab7 604 (calendar-extract-day s-s))
f2268dc0
GM
605 "Shabbat Shirah")
606 (and (progn
607 (setq m displayed-month
608 y displayed-year
609 year (progn
e803eab7
GM
610 (calendar-increment-month m y -1)
611 (calendar-extract-year
f2268dc0
GM
612 (calendar-julian-from-absolute
613 (calendar-absolute-from-gregorian (list m 1 y))))))
614 (= 21 (% year 28)))
615 (holiday-julian 3 26 "Kiddush HaHamah")))))
616
617
711d00e7 618(autoload 'diary-list-entries-1 "diary-lib")
c3efd659 619
28b3c0f5 620;;;###diary-autoload
8fc9e5a0 621(defun diary-hebrew-list-entries ()
4b112ac4 622 "Add any Hebrew date entries from the diary file to `diary-entries-list'.
0e96e25f 623Hebrew date diary entries must be prefaced by `diary-hebrew-entry-symbol'
8f11970d
GM
624\(normally an `H'). The same diary date forms govern the style
625of the Hebrew calendar entries, except that the Hebrew month
872edde5 626names cannot be abbreviated. The Hebrew months are numbered
8f11970d
GM
627from 1 to 13 with Nisan being 1, 12 being Adar I and 13 being
628Adar II; you must use `Adar I' if you want Adar of a common
629Hebrew year. If a Hebrew date diary entry begins with
630`diary-nonmarking-symbol', the entry will appear in the diary
631listing, but will not be marked in the calendar. This function
9ee4e581 632is provided for use with `diary-nongregorian-listing-hook'."
711d00e7 633 (diary-list-entries-1 calendar-hebrew-month-name-array-leap-year
0e96e25f 634 diary-hebrew-entry-symbol
711d00e7 635 'calendar-hebrew-from-absolute))
8fc9e5a0
GM
636;;;###diary-autoload
637(define-obsolete-function-alias 'list-hebrew-diary-entries
638 'diary-hebrew-list-entries "23.1")
4b112ac4 639
28c02796
GM
640(autoload 'calendar-mark-complex "diary-lib")
641
28b3c0f5 642;;;###diary-autoload
8fc9e5a0 643(defun calendar-hebrew-mark-date-pattern (month day year &optional color)
da3fc020 644 "Mark dates in calendar window that conform to Hebrew date MONTH/DAY/YEAR.
28c02796 645A value of 0 in any position is a wildcard. Optional argument COLOR is
e803eab7 646passed to `calendar-mark-visible-date' as MARK."
28c02796
GM
647 ;; FIXME not the same as the Bahai and Islamic cases, so can't use
648 ;; calendar-mark-1.
937e6a56 649 (with-current-buffer calendar-buffer
0d1bb2ff
GM
650 (if (and (not (zerop month)) (not (zerop day)))
651 (if (not (zerop year))
da3fc020
GM
652 ;; Fully specified Hebrew date.
653 (let ((date (calendar-gregorian-from-absolute
8fc9e5a0 654 (calendar-hebrew-to-absolute
da3fc020
GM
655 (list month day year)))))
656 (if (calendar-date-is-visible-p date)
e803eab7 657 (calendar-mark-visible-date date color)))
6b789b4b
GM
658 ;; Month and day in any year.
659 (let ((gdate (calendar-hebrew-date-is-visible-p month day)))
e803eab7 660 (if gdate (calendar-mark-visible-date gdate color))))
28c02796
GM
661 (calendar-mark-complex month day year
662 'calendar-hebrew-from-absolute color))))
da3fc020 663
8fc9e5a0
GM
664;;;###diary-autoload
665(define-obsolete-function-alias 'mark-hebrew-calendar-date-pattern
666 'calendar-hebrew-mark-date-pattern "23.1")
667
711d00e7 668(autoload 'diary-mark-entries-1 "diary-lib")
e475d400 669
28b3c0f5 670;;;###diary-autoload
8fc9e5a0 671(defun diary-hebrew-mark-entries ()
4b112ac4 672 "Mark days in the calendar window that have Hebrew date diary entries.
711d00e7
GM
673Marks each entry in `diary-file' (or included files) visible in the calendar
674window. See `list-hebrew-diary-entries' for more information."
8fc9e5a0 675 (diary-mark-entries-1 'calendar-hebrew-mark-date-pattern
618c03c1 676 calendar-hebrew-month-name-array-leap-year
0e96e25f 677 diary-hebrew-entry-symbol
618c03c1 678 'calendar-hebrew-from-absolute))
4b112ac4 679
8fc9e5a0
GM
680;;;###diary-autoload
681(define-obsolete-function-alias 'mark-hebrew-diary-entries
682 'diary-hebrew-mark-entries "23.1")
f2b46435
GM
683
684(autoload 'diary-insert-entry-1 "diary-lib")
685
28b3c0f5 686;;;###cal-autoload
8fc9e5a0
GM
687(defun diary-hebrew-insert-entry (arg)
688 "Insert a diary entry for the Hebrew date at point.
6afe7cdd 689Prefix argument ARG makes the entry nonmarking."
4b112ac4 690 (interactive "P")
f2b46435 691 (diary-insert-entry-1 nil arg calendar-hebrew-month-name-array-leap-year
0e96e25f 692 diary-hebrew-entry-symbol
f2b46435 693 'calendar-hebrew-from-absolute))
4b112ac4 694
8fc9e5a0
GM
695;;;###diary-autoload
696(define-obsolete-function-alias 'insert-hebrew-diary-entry
697 'diary-hebrew-insert-entry "23.1")
698
28b3c0f5 699;;;###cal-autoload
8fc9e5a0 700(defun diary-hebrew-insert-monthly-entry (arg)
4b112ac4
ER
701 "Insert a monthly diary entry.
702For the day of the Hebrew month corresponding to the date indicated by point.
6afe7cdd 703Prefix argument ARG makes the entry nonmarking."
4b112ac4 704 (interactive "P")
f2b46435 705 (diary-insert-entry-1 'monthly arg calendar-hebrew-month-name-array-leap-year
0e96e25f 706 diary-hebrew-entry-symbol
f2b46435 707 'calendar-hebrew-from-absolute))
8fc9e5a0
GM
708;;;###diary-autoload
709(define-obsolete-function-alias 'insert-monthly-hebrew-diary-entry
710 'diary-hebrew-insert-monthly-entry "23.1")
4b112ac4 711
28b3c0f5 712;;;###cal-autoload
8fc9e5a0 713(defun diary-hebrew-insert-yearly-entry (arg)
4b112ac4
ER
714 "Insert an annual diary entry.
715For the day of the Hebrew year corresponding to the date indicated by point.
6afe7cdd 716Prefix argument ARG makes the entry nonmarking."
4b112ac4 717 (interactive "P")
f2b46435 718 (diary-insert-entry-1 'yearly arg calendar-hebrew-month-name-array-leap-year
0e96e25f 719 diary-hebrew-entry-symbol
f2b46435 720 'calendar-hebrew-from-absolute))
8fc9e5a0
GM
721;;;###diary-autoload
722(define-obsolete-function-alias 'insert-yearly-hebrew-diary-entry
723 'diary-hebrew-insert-yearly-entry "23.1")
4b112ac4
ER
724
725;;;###autoload
4e740fd0 726(defun calendar-hebrew-list-yahrzeits (death-date start-year end-year)
4b112ac4
ER
727 "List Yahrzeit dates for *Gregorian* DEATH-DATE from START-YEAR to END-YEAR.
728When called interactively from the calendar window, the date of death is taken
729from the cursor position."
730 (interactive
731 (let* ((death-date
732 (if (equal (current-buffer) (get-buffer calendar-buffer))
733 (calendar-cursor-to-date)
734 (let* ((today (calendar-current-date))
735 (year (calendar-read
736 "Year of death (>0): "
c645b7bb 737 (lambda (x) (> x 0))
d92bcf94 738 (number-to-string (calendar-extract-year today))))
4b112ac4
ER
739 (month-array calendar-month-name-array)
740 (completion-ignore-case t)
abe4091c 741 (month (cdr (assoc-string
bf7b2caf
RS
742 (completing-read
743 "Month of death (name): "
744 (mapcar 'list (append month-array nil))
745 nil t)
abe4091c 746 (calendar-make-alist month-array 1) t)))
4b112ac4
ER
747 (last (calendar-last-day-of-month month year))
748 (day (calendar-read
749 (format "Day of death (1-%d): " last)
c645b7bb 750 (lambda (x) (and (< 0 x) (<= x last))))))
4b112ac4 751 (list month day year))))
e803eab7 752 (death-year (calendar-extract-year death-date))
4b112ac4
ER
753 (start-year (calendar-read
754 (format "Starting year of Yahrzeit table (>%d): "
755 death-year)
c645b7bb 756 (lambda (x) (> x death-year))
d92bcf94 757 (number-to-string (1+ death-year))))
4b112ac4
ER
758 (end-year (calendar-read
759 (format "Ending year of Yahrzeit table (>=%d): "
760 start-year)
71ea27ee
GM
761 (lambda (x) (>= x start-year)))))
762 (list death-date start-year end-year)))
6afe7cdd 763 (message "Computing Yahrzeits...")
66471e03 764 (let* ((h-date (calendar-hebrew-from-absolute
4b112ac4 765 (calendar-absolute-from-gregorian death-date)))
e803eab7
GM
766 (h-month (calendar-extract-month h-date))
767 (h-day (calendar-extract-day h-date))
768 (h-year (calendar-extract-year h-date))
2d354894 769 (i (1- start-year)))
e803eab7 770 (calendar-in-read-only-buffer calendar-hebrew-yahrzeit-buffer
318a5488
GM
771 (calendar-set-mode-line
772 (format "Yahrzeit dates for %s = %s"
773 (calendar-date-string death-date)
774 (let ((calendar-month-name-array
8fc9e5a0 775 (if (calendar-hebrew-leap-year-p h-year)
318a5488
GM
776 calendar-hebrew-month-name-array-leap-year
777 calendar-hebrew-month-name-array-common-year)))
778 (calendar-date-string h-date nil t))))
2d354894 779 (while (<= (setq i (1+ i)) end-year)
318a5488
GM
780 (insert
781 (calendar-date-string
782 (calendar-gregorian-from-absolute
8fc9e5a0 783 (calendar-hebrew-yahrzeit
318a5488 784 h-date
e803eab7 785 (calendar-extract-year
318a5488 786 (calendar-hebrew-from-absolute
2d354894
GM
787 (calendar-absolute-from-gregorian (list 1 1 i))))))) "\n"))))
788 (message "Computing Yahrzeits...done"))
4b112ac4 789
8fc9e5a0
GM
790;;;###autoload
791(define-obsolete-function-alias 'list-yahrzeit-dates
4e740fd0 792 'calendar-hebrew-list-yahrzeits "23.1")
8fc9e5a0 793
c3efd659
GM
794(defvar date)
795
9ee4e581 796;; To be called from diary-list-sexp-entries, where DATE is bound.
28b3c0f5 797;;;###diary-autoload
4b112ac4
ER
798(defun diary-hebrew-date ()
799 "Hebrew calendar equivalent of date diary entry."
800 (format "Hebrew date (until sunset): %s" (calendar-hebrew-date-string date)))
801
28b3c0f5 802;;;###diary-autoload
8fc9e5a0 803(defun diary-hebrew-omer (&optional mark)
4b112ac4 804 "Omer count diary entry.
9a27723c
RS
805Entry applies if date is within 50 days after Passover.
806
a1506d29 807An optional parameter MARK specifies a face or single-character string to
9a27723c 808use when highlighting the day in the calendar."
4b112ac4 809 (let* ((passover
8fc9e5a0 810 (calendar-hebrew-to-absolute
e803eab7 811 (list 1 15 (+ (calendar-extract-year date) 3760))))
4b112ac4
ER
812 (omer (- (calendar-absolute-from-gregorian date) passover))
813 (week (/ omer 7))
814 (day (% omer 7)))
815 (if (and (> omer 0) (< omer 50))
a1506d29 816 (cons mark
71ea27ee
GM
817 (format "Day %d%s of the omer (until sunset)"
818 omer
819 (if (zerop week)
820 ""
821 (format ", that is, %d week%s%s"
822 week
823 (if (= week 1) "" "s")
824 (if (zerop day)
825 ""
826 (format " and %d day%s"
827 day (if (= day 1) "" "s"))))))))))
8fc9e5a0
GM
828;;;###diary-autoload
829(define-obsolete-function-alias 'diary-omer 'diary-hebrew-omer "23.1")
4b112ac4 830
c3efd659
GM
831(defvar entry)
832
f2b46435
GM
833(autoload 'diary-make-date "diary-lib")
834
b4cb42a4
GM
835(declare-function diary-ordinal-suffix "diary-lib" (n))
836
28b3c0f5 837;;;###diary-autoload
8fc9e5a0 838(defun diary-hebrew-yahrzeit (death-month death-day death-year &optional mark)
6afe7cdd 839 "Yahrzeit diary entry--entry applies if date is Yahrzeit or the day before.
f2b46435
GM
840Parameters are DEATH-MONTH, DEATH-DAY, DEATH-YEAR; the diary
841entry is assumed to be the name of the person. Although the date
842of death is specified by the civil calendar, the proper Hebrew
843calendar Yahrzeit is determined.
844
845The order of the input parameters changes according to `calendar-date-style'
846\(e.g. to DEATH-DAY, DEATH-MONTH, DEATH-YEAR in the European style).
9a27723c 847
a1506d29 848An optional parameter MARK specifies a face or single-character string to
9a27723c 849use when highlighting the day in the calendar."
4b112ac4
ER
850 (let* ((h-date (calendar-hebrew-from-absolute
851 (calendar-absolute-from-gregorian
f2b46435 852 (diary-make-date death-month death-day death-year))))
e803eab7
GM
853 (h-month (calendar-extract-month h-date))
854 (h-day (calendar-extract-day h-date))
855 (h-year (calendar-extract-year h-date))
4b112ac4 856 (d (calendar-absolute-from-gregorian date))
e803eab7 857 (yr (calendar-extract-year (calendar-hebrew-from-absolute d)))
4b112ac4 858 (diff (- yr h-year))
8fc9e5a0 859 (y (calendar-hebrew-yahrzeit h-date yr)))
4b112ac4 860 (if (and (> diff 0) (or (= y d) (= y (1+ d))))
9a27723c 861 (cons mark
71ea27ee
GM
862 (format "Yahrzeit of %s%s: %d%s anniversary"
863 entry
864 (if (= y d) "" " (evening)")
865 diff
4980d28f
GM
866 (diary-ordinal-suffix diff))))))
867
8fc9e5a0
GM
868;;;###diary-autoload
869(define-obsolete-function-alias 'diary-yahrzeit 'diary-hebrew-yahrzeit "23.1")
4b112ac4 870
28b3c0f5 871;;;###diary-autoload
8fc9e5a0 872(defun diary-hebrew-rosh-hodesh (&optional mark)
4b112ac4 873 "Rosh Hodesh diary entry.
9a27723c
RS
874Entry applies if date is Rosh Hodesh, the day before, or the Saturday before.
875
a1506d29 876An optional parameter MARK specifies a face or single-character string to
9a27723c 877use when highlighting the day in the calendar."
4b112ac4
ER
878 (let* ((d (calendar-absolute-from-gregorian date))
879 (h-date (calendar-hebrew-from-absolute d))
e803eab7
GM
880 (h-month (calendar-extract-month h-date))
881 (h-day (calendar-extract-day h-date))
882 (h-year (calendar-extract-year h-date))
8fc9e5a0
GM
883 (leap-year (calendar-hebrew-leap-year-p h-year))
884 (last-day (calendar-hebrew-last-day-of-month h-month h-year))
4b112ac4
ER
885 (h-month-names
886 (if leap-year
887 calendar-hebrew-month-name-array-leap-year
888 calendar-hebrew-month-name-array-common-year))
889 (this-month (aref h-month-names (1- h-month)))
e803eab7 890 (h-yesterday (calendar-extract-day
4b112ac4
ER
891 (calendar-hebrew-from-absolute (1- d)))))
892 (if (or (= h-day 30) (and (= h-day 1) (/= h-month 7)))
a1506d29 893 (cons mark
71ea27ee
GM
894 (format
895 "Rosh Hodesh %s"
896 (if (= h-day 30)
897 (format
898 "%s (first day)"
899 ;; Next month must be in the same year since this
900 ;; month can't be the last month of the year since
901 ;; it has 30 days
902 (aref h-month-names h-month))
903 (if (= h-yesterday 30)
904 (format "%s (second day)" this-month)
905 this-month))))
906 (if (= (% d 7) 6) ; Saturday--check for Shabbat Mevarchim
a1506d29 907 (cons mark
71ea27ee
GM
908 (cond ((and (> h-day 22) (/= h-month 6) (= 29 last-day))
909 (format "Mevarchim Rosh Hodesh %s (%s)"
910 (aref h-month-names
911 (if (= h-month
8fc9e5a0 912 (calendar-hebrew-last-month-of-year
71ea27ee
GM
913 h-year))
914 0 h-month))
915 (aref calendar-day-name-array (- 29 h-day))))
916 ((and (< h-day 30) (> h-day 22) (= 30 last-day))
917 (format "Mevarchim Rosh Hodesh %s (%s-%s)"
918 (aref h-month-names h-month)
919 (if (= h-day 29)
920 "tomorrow"
921 (aref calendar-day-name-array (- 29 h-day)))
922 (aref calendar-day-name-array
923 (% (- 30 h-day) 7))))))
4b112ac4 924 (if (and (= h-day 29) (/= h-month 6))
347a0e23 925 (cons mark
71ea27ee
GM
926 (format "Erev Rosh Hodesh %s"
927 (aref h-month-names
928 (if (= h-month
8fc9e5a0 929 (calendar-hebrew-last-month-of-year
71ea27ee
GM
930 h-year))
931 0 h-month)))))))))
8fc9e5a0
GM
932;;;###diary-autoload
933(define-obsolete-function-alias 'diary-rosh-hodesh
934 'diary-hebrew-rosh-hodesh "23.1")
9a27723c 935
8fc9e5a0 936(defconst calendar-hebrew-parashiot-names
71ea27ee
GM
937 ["Bereshith" "Noah" "Lech L'cha" "Vayera" "Hayei Sarah" "Toledoth"
938 "Vayetze" "Vayishlah" "Vayeshev" "Mikketz" "Vayiggash" "Vayhi"
939 "Shemoth" "Vaera" "Bo" "Beshallah" "Yithro" "Mishpatim"
940 "Terumah" "Tetzavveh" "Ki Tissa" "Vayakhel" "Pekudei" "Vayikra"
941 "Tzav" "Shemini" "Tazria" "Metzora" "Aharei Moth" "Kedoshim"
942 "Emor" "Behar" "Behukkotai" "Bemidbar" "Naso" "Behaalot'cha"
943 "Shelah L'cha" "Korah" "Hukkath" "Balak" "Pinhas" "Mattoth"
944 "Masei" "Devarim" "Vaethanan" "Ekev" "Reeh" "Shofetim"
945 "Ki Tetze" "Ki Tavo" "Nitzavim" "Vayelech" "Haazinu"]
da3fc020
GM
946 "The names of the parashiot in the Torah.")
947
8fc9e5a0 948(defun calendar-hebrew-parasha-name (p)
da3fc020 949 "Name(s) corresponding to parasha P."
71ea27ee 950 (if (arrayp p) ; combined parasha
da3fc020 951 (format "%s/%s"
8fc9e5a0
GM
952 (aref calendar-hebrew-parashiot-names (aref p 0))
953 (aref calendar-hebrew-parashiot-names (aref p 1)))
954 (aref calendar-hebrew-parashiot-names p)))
da3fc020 955
711d00e7 956;; Following 14 constants are used in diary-parasha (intern).
8f11970d 957
9c68082d 958;; The seven ordinary year types (keviot).
8fc9e5a0 959(defconst calendar-hebrew-year-Saturday-incomplete-Sunday
4b112ac4 960 [nil 52 nil nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 [21 22]
71ea27ee
GM
961 23 24 nil 25 [26 27] [28 29] 30 [31 32] 33 34 35 36 37 38 39 40 [41 42]
962 43 44 45 46 47 48 49 50]
4b112ac4
ER
963 "The structure of the parashiot.
964Hebrew year starts on Saturday, is `incomplete' (Heshvan and Kislev each have
96529 days), and has Passover start on Sunday.")
966
8fc9e5a0 967(defconst calendar-hebrew-year-Saturday-complete-Tuesday
4b112ac4 968 [nil 52 nil nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 [21 22]
71ea27ee
GM
969 23 24 nil 25 [26 27] [28 29] 30 [31 32] 33 34 35 36 37 38 39 40 [41 42]
970 43 44 45 46 47 48 49 [50 51]]
4b112ac4
ER
971 "The structure of the parashiot.
972Hebrew year that starts on Saturday, is `complete' (Heshvan and Kislev each
973have 30 days), and has Passover start on Tuesday.")
974
8fc9e5a0 975(defconst calendar-hebrew-year-Monday-incomplete-Tuesday
4b112ac4 976 [51 52 nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 [21 22]
71ea27ee
GM
977 23 24 nil 25 [26 27] [28 29] 30 [31 32] 33 34 35 36 37 38 39 40 [41 42]
978 43 44 45 46 47 48 49 [50 51]]
4b112ac4
ER
979 "The structure of the parashiot.
980Hebrew year that starts on Monday, is `incomplete' (Heshvan and Kislev each
981have 29 days), and has Passover start on Tuesday.")
982
8fc9e5a0 983(defconst calendar-hebrew-year-Monday-complete-Thursday
4b112ac4 984 [51 52 nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 [21 22]
71ea27ee
GM
985 23 24 nil 25 [26 27] [28 29] 30 [31 32] 33 (nil . 34) (34 . 35) (35 . 36)
986 (36 . 37) (37 . 38) ([38 39] . 39) 40 [41 42] 43 44 45 46 47 48 49 [50 51]]
4b112ac4
ER
987 "The structure of the parashiot.
988Hebrew year that starts on Monday, is `complete' (Heshvan and Kislev each have
98930 days), and has Passover start on Thursday.")
990
8fc9e5a0 991(defconst calendar-hebrew-year-Tuesday-regular-Thursday
4b112ac4 992 [51 52 nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 [21 22]
71ea27ee
GM
993 23 24 nil 25 [26 27] [28 29] 30 [31 32] 33 (nil . 34) (34 . 35) (35 . 36)
994 (36 . 37) (37 . 38) ([38 39] . 39) 40 [41 42] 43 44 45 46 47 48 49 [50 51]]
4b112ac4
ER
995 "The structure of the parashiot.
996Hebrew year that starts on Tuesday, is `regular' (Heshvan has 29 days and
997Kislev has 30 days), and has Passover start on Thursday.")
998
8fc9e5a0 999(defconst calendar-hebrew-year-Thursday-regular-Saturday
4b112ac4 1000 [52 nil nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 [21 22] 23
71ea27ee
GM
1001 24 nil (nil . 25) (25 . [26 27]) ([26 27] . [28 29]) ([28 29] . 30)
1002 (30 . 31) ([31 32] . 32) 33 34 35 36 37 38 39 40 [41 42] 43 44 45 46 47 48
1003 49 50]
4b112ac4
ER
1004 "The structure of the parashiot.
1005Hebrew year that starts on Thursday, is `regular' (Heshvan has 29 days and
1006Kislev has 30 days), and has Passover start on Saturday.")
1007
8fc9e5a0 1008(defconst calendar-hebrew-year-Thursday-complete-Sunday
4b112ac4 1009 [52 nil nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
71ea27ee
GM
1010 23 24 nil 25 [26 27] [28 29] 30 [31 32] 33 34 35 36 37 38 39 40 [41 42]
1011 43 44 45 46 47 48 49 50]
4b112ac4
ER
1012 "The structure of the parashiot.
1013Hebrew year that starts on Thursday, is `complete' (Heshvan and Kislev each
1014have 30 days), and has Passover start on Sunday.")
1015
9c68082d 1016;; The seven leap year types (keviot).
8fc9e5a0 1017(defconst calendar-hebrew-year-Saturday-incomplete-Tuesday
4b112ac4 1018 [nil 52 nil nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
71ea27ee
GM
1019 23 24 25 26 27 nil 28 29 30 31 32 33 34 35 36 37 38 39 40 [41 42]
1020 43 44 45 46 47 48 49 [50 51]]
4b112ac4
ER
1021 "The structure of the parashiot.
1022Hebrew year that starts on Saturday, is `incomplete' (Heshvan and Kislev each
1023have 29 days), and has Passover start on Tuesday.")
1024
8fc9e5a0 1025(defconst calendar-hebrew-year-Saturday-complete-Thursday
4b112ac4 1026 [nil 52 nil nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
71ea27ee
GM
1027 23 24 25 26 27 nil 28 29 30 31 32 33 (nil . 34) (34 . 35) (35 . 36)
1028 (36 . 37) (37 . 38) ([38 39] . 39) 40 [41 42] 43 44 45 46 47 48 49 [50 51]]
4b112ac4
ER
1029 "The structure of the parashiot.
1030Hebrew year that starts on Saturday, is `complete' (Heshvan and Kislev each
1031have 30 days), and has Passover start on Thursday.")
1032
8fc9e5a0 1033(defconst calendar-hebrew-year-Monday-incomplete-Thursday
4b112ac4 1034 [51 52 nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
71ea27ee
GM
1035 23 24 25 26 27 nil 28 29 30 31 32 33 (nil . 34) (34 . 35) (35 . 36)
1036 (36 . 37) (37 . 38) ([38 39] . 39) 40 [41 42] 43 44 45 46 47 48 49 [50 51]]
4b112ac4
ER
1037 "The structure of the parashiot.
1038Hebrew year that starts on Monday, is `incomplete' (Heshvan and Kislev each
1039have 29 days), and has Passover start on Thursday.")
1040
8fc9e5a0 1041(defconst calendar-hebrew-year-Monday-complete-Saturday
4b112ac4 1042 [51 52 nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
71ea27ee
GM
1043 23 24 25 26 27 nil (nil . 28) (28 . 29) (29 . 30) (30 . 31) (31 . 32)
1044 (32 . 33) (33 . 34) (34 . 35) (35 . 36) (36 . 37) (37 . 38) (38 . 39)
1045 (39 . 40) (40 . 41) ([41 42] . 42) 43 44 45 46 47 48 49 50]
4b112ac4
ER
1046 "The structure of the parashiot.
1047Hebrew year that starts on Monday, is `complete' (Heshvan and Kislev each have
104830 days), and has Passover start on Saturday.")
1049
8fc9e5a0 1050(defconst calendar-hebrew-year-Tuesday-regular-Saturday
4b112ac4 1051 [51 52 nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
71ea27ee
GM
1052 23 24 25 26 27 nil (nil . 28) (28 . 29) (29 . 30) (30 . 31) (31 . 32)
1053 (32 . 33) (33 . 34) (34 . 35) (35 . 36) (36 . 37) (37 . 38) (38 . 39)
1054 (39 . 40) (40 . 41) ([41 42] . 42) 43 44 45 46 47 48 49 50]
4b112ac4
ER
1055 "The structure of the parashiot.
1056Hebrew year that starts on Tuesday, is `regular' (Heshvan has 29 days and
1057Kislev has 30 days), and has Passover start on Saturday.")
1058
8fc9e5a0 1059(defconst calendar-hebrew-year-Thursday-incomplete-Sunday
4b112ac4 1060 [52 nil nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
71ea27ee
GM
1061 23 24 25 26 27 28 nil 29 30 31 32 33 34 35 36 37 38 39 40 41 42
1062 43 44 45 46 47 48 49 50]
4b112ac4
ER
1063 "The structure of the parashiot.
1064Hebrew year that starts on Thursday, is `incomplete' (Heshvan and Kislev both
1065have 29 days), and has Passover start on Sunday.")
1066
8fc9e5a0 1067(defconst calendar-hebrew-year-Thursday-complete-Tuesday
4b112ac4 1068 [52 nil nil 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
71ea27ee
GM
1069 23 24 25 26 27 28 nil 29 30 31 32 33 34 35 36 37 38 39 40 41 42
1070 43 44 45 46 47 48 49 [50 51]]
4b112ac4
ER
1071 "The structure of the parashiot.
1072Hebrew year that starts on Thursday, is `complete' (Heshvan and Kislev both
1073have 30 days), and has Passover start on Tuesday.")
1074
711d00e7 1075;;;###diary-autoload
8fc9e5a0 1076(defun diary-hebrew-parasha (&optional mark)
711d00e7
GM
1077 "Parasha diary entry--entry applies if date is a Saturday.
1078An optional parameter MARK specifies a face or single-character string to
1079use when highlighting the day in the calendar."
1080 (let ((d (calendar-absolute-from-gregorian date)))
1081 (if (= (% d 7) 6) ; Saturday
e803eab7 1082 (let* ((h-year (calendar-extract-year
711d00e7
GM
1083 (calendar-hebrew-from-absolute d)))
1084 (rosh-hashanah
8fc9e5a0 1085 (calendar-hebrew-to-absolute (list 7 1 h-year)))
711d00e7 1086 (passover
8fc9e5a0 1087 (calendar-hebrew-to-absolute (list 1 15 h-year)))
711d00e7
GM
1088 (rosh-hashanah-day
1089 (aref calendar-day-name-array (% rosh-hashanah 7)))
1090 (passover-day
1091 (aref calendar-day-name-array (% passover 7)))
8fc9e5a0
GM
1092 (long-h (calendar-hebrew-long-heshvan-p h-year))
1093 (short-k (calendar-hebrew-short-kislev-p h-year))
711d00e7
GM
1094 (type (cond ((and long-h (not short-k)) "complete")
1095 ((and (not long-h) short-k) "incomplete")
1096 (t "regular")))
1097 (year-format
1098 (symbol-value
8fc9e5a0 1099 (intern (format "calendar-hebrew-year-%s-%s-%s" ; keviah
711d00e7
GM
1100 rosh-hashanah-day type passover-day))))
1101 (first-saturday ; of Hebrew year
1102 (calendar-dayname-on-or-before 6 (+ 6 rosh-hashanah)))
1103 (saturday ; which Saturday of the Hebrew year
1104 (/ (- d first-saturday) 7))
1105 (parasha (aref year-format saturday)))
1106 (if parasha
1107 (cons mark
1108 (format
1109 "Parashat %s"
1110 (if (listp parasha) ; Israel differs from diaspora
1111 (if (car parasha)
1112 (format "%s (diaspora), %s (Israel)"
8fc9e5a0 1113 (calendar-hebrew-parasha-name
711d00e7 1114 (car parasha))
8fc9e5a0 1115 (calendar-hebrew-parasha-name
711d00e7
GM
1116 (cdr parasha)))
1117 (format "%s (Israel)"
8fc9e5a0 1118 (calendar-hebrew-parasha-name
711d00e7 1119 (cdr parasha))))
8fc9e5a0
GM
1120 (calendar-hebrew-parasha-name parasha)))))))))
1121
1122(define-obsolete-function-alias 'diary-parasha 'diary-hebrew-parasha "23.1")
711d00e7 1123
87e1e9cd
GM
1124
1125(declare-function solar-setup "solar" ())
1126(declare-function solar-sunrise-sunset "solar" (date))
1127(defvar calendar-latitude)
1128(defvar calendar-longitude)
1129(defvar calendar-time-zone)
1130
1131
9ee4e581 1132;; To be called from diary-list-sexp-entries, where DATE is bound.
87e1e9cd
GM
1133;;;###diary-autoload
1134(defun diary-hebrew-sabbath-candles (&optional mark)
1135 "Local time of candle lighting diary entry--applies if date is a Friday.
1136No diary entry if there is no sunset on that date. Uses
1137`diary-hebrew-sabbath-candles-minutes'.
1138
1139An optional parameter MARK specifies a face or single-character string to
1140use when highlighting the day in the calendar."
1141 (require 'solar)
1142 (or (and calendar-latitude calendar-longitude calendar-time-zone)
1143 (solar-setup))
1144 (if (= (% (calendar-absolute-from-gregorian date) 7) 5) ; Friday
d347df4f 1145 (let ((sunset (cadr (solar-sunrise-sunset date))))
87e1e9cd 1146 (if sunset
d347df4f
GM
1147 (cons mark (format
1148 "%s Sabbath candle lighting"
1149 (apply 'solar-time-string
1150 (cons (- (car sunset)
1151 (/ diary-hebrew-sabbath-candles-minutes
1152 60.0))
1153 (cdr sunset)))))))))
87e1e9cd
GM
1154
1155;;;###diary-autoload
1156(define-obsolete-function-alias 'diary-sabbath-candles
1157 'diary-hebrew-sabbath-candles "23.1")
1158
1159
4b112ac4
ER
1160(provide 'cal-hebrew)
1161
c645b7bb 1162;; arch-tag: aaab6718-7712-42ac-a32d-28fe1f944f3c
4b112ac4 1163;;; cal-hebrew.el ends here