From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.org!.POSTED.blaine.gmane.org!not-for-mail From: Boruch Baum Newsgroups: gmane.emacs.bugs Subject: bug#39002: [feature requests] calendar-hebrew [code included] Date: Tue, 7 Jan 2020 01:28:30 -0500 Message-ID: <20200107062830.kyzjn43p4i3fmdzz@E15-2016.optimum.net> Mime-Version: 1.0 Content-Type: multipart/mixed; boundary="egj6aogtrfgv725c" Injection-Info: blaine.gmane.org; posting-host="blaine.gmane.org:195.159.176.226"; logging-data="203353"; mail-complaints-to="usenet@blaine.gmane.org" User-Agent: NeoMutt/20180716 To: 39002@debbugs.gnu.org Original-X-From: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane.org@gnu.org Tue Jan 07 07:30:18 2020 Return-path: Envelope-to: geb-bug-gnu-emacs@m.gmane.org Original-Received: from lists.gnu.org ([209.51.188.17]) by blaine.gmane.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.89) (envelope-from ) id 1ioiNK-000q14-KI for geb-bug-gnu-emacs@m.gmane.org; Tue, 07 Jan 2020 07:29:59 +0100 Original-Received: from localhost ([::1]:42976 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1ioiNH-0006pF-AF for geb-bug-gnu-emacs@m.gmane.org; Tue, 07 Jan 2020 01:29:55 -0500 Original-Received: from eggs.gnu.org ([2001:470:142:3::10]:37851) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1ioiMT-0006Ux-7B for bug-gnu-emacs@gnu.org; Tue, 07 Jan 2020 01:29:07 -0500 Original-Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1ioiMQ-0005cR-Ka for bug-gnu-emacs@gnu.org; Tue, 07 Jan 2020 01:29:05 -0500 Original-Received: from debbugs.gnu.org ([209.51.188.43]:41216) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1ioiMQ-0005c3-FT for bug-gnu-emacs@gnu.org; Tue, 07 Jan 2020 01:29:02 -0500 Original-Received: from Debian-debbugs by debbugs.gnu.org with local (Exim 4.84_2) (envelope-from ) id 1ioiMQ-0000Hi-C7 for bug-gnu-emacs@gnu.org; Tue, 07 Jan 2020 01:29:02 -0500 X-Loop: help-debbugs@gnu.org Resent-From: Boruch Baum Original-Sender: "Debbugs-submit" Resent-CC: bug-gnu-emacs@gnu.org Resent-Date: Tue, 07 Jan 2020 06:29:02 +0000 Resent-Message-ID: Resent-Sender: help-debbugs@gnu.org X-GNU-PR-Message: report 39002 X-GNU-PR-Package: emacs X-Debbugs-Original-To: Emacs Bug Reporting Original-Received: via spool by submit@debbugs.gnu.org id=B.15783785271061 (code B ref -1); Tue, 07 Jan 2020 06:29:02 +0000 Original-Received: (at submit) by debbugs.gnu.org; 7 Jan 2020 06:28:47 +0000 Original-Received: from localhost ([127.0.0.1]:47189 helo=debbugs.gnu.org) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1ioiMA-0000H1-Rl for submit@debbugs.gnu.org; Tue, 07 Jan 2020 01:28:47 -0500 Original-Received: from lists.gnu.org ([209.51.188.17]:41136) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1ioiM8-0000Gs-Ka for submit@debbugs.gnu.org; Tue, 07 Jan 2020 01:28:45 -0500 Original-Received: from eggs.gnu.org ([2001:470:142:3::10]:37759) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1ioiM3-0005O4-MN for bug-gnu-emacs@gnu.org; Tue, 07 Jan 2020 01:28:42 -0500 Original-Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1ioiM1-0005DW-5a for bug-gnu-emacs@gnu.org; Tue, 07 Jan 2020 01:28:39 -0500 Original-Received: from mout.gmx.net ([212.227.17.20]:46893) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1ioiM0-0005CD-Id for bug-gnu-emacs@gnu.org; Tue, 07 Jan 2020 01:28:37 -0500 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=gmx.net; s=badeba3b8450; t=1578378513; bh=MKvVycYwI6B5vlD+HyGKifBUf09bztA29tCCLkVUL3A=; h=X-UI-Sender-Class:Date:From:To:Subject; b=AGK0RzConjKWsKOOmQybbZlO5cyH6YwLLiBIAI6O08rVo6GZywXTfAdXrBEkviBs9 1JqETpVWPX8cv/K2wM0wZZQYbN29/suKd9H+pVtK0UdXYIRgyrwmwzvS04/tA6TL91 cvBTZxwovFaw7+dW9ePRIdJE2/Dem0jMfDqaVdvQ= X-UI-Sender-Class: 01bb95c1-4bf8-414a-932a-4f6e2808ef9c Original-Received: from E15-2016.optimum.net ([96.246.226.236]) by mail.gmx.com (mrgmx105 [212.227.17.174]) with ESMTPSA (Nemesis) id 1N3bSt-1jpJEg1T63-010ZvP for ; Tue, 07 Jan 2020 07:28:33 +0100 Content-Disposition: inline X-Provags-ID: V03:K1:3Jia/lk3d0M86H+6E19ANhDilArdBGT5NMTLcpI5K3mxdL80Gdj BCr2UC6RF9BatESKBKZ90DSiCDUCDI1ZIqAdDnF0L6c9QeEJOGtsoBNlJueSJJS1qPCMzow u7pJRk7VDidDvW0f4Pk08lvVlCdCX88N+XyxR66BiaV7ysA9UZv9aoZ6oyaaY2PKbkIVF3O Vfd7X6vnlqnQFI2co8b5Q== X-UI-Out-Filterresults: notjunk:1;V03:K0:xT0x4fKYtbc=:kIFJaDJl6okIOAB4lo6f6s +cSUsTf1HaaWlivnl2pDl8H90M6AwEvZfaIkdS4whEKNTKgJybj4BIi+gP5SU7AJT1Mw72+5F E4VPd/So28sG4j0gojJ7orU53EXp7n8f1TTxP+NLhqg0eu+zRw/CfMpIM7/nmABEu+4RHV1fO zmIjOTDoSogX31VUT6EZG2jeRFcmb5sbNe9r0ChtuuMdbER16jhMfIcVzAaPTIa4185EXIbRn M5dd+EthvOkQy7MtUuBsWVwmihDGiUABSmc8mbK3rA4gOV4IUlp21/yeETW9Whf9yAV9Rj2Op 1DHdHzaq8XNaoHUoAgoLmgs4VAY/64o/DKM6Z35VFpO+qqrELhOa+DQWDiSNZ4K2oI+07K8Vu flrdVeB+XbHaOLBwKwbISpBzsyFkmECmIOvPKcxEBqfyWCb/e0u6vGVKSntr6QCOhCkjOlsP6 6BOdQohDbPNOnMlC+/looTBf0uVH9OAKVP1bBKXvEPkthU2ORtVOqnEIsS3Xn84n60cerRkLO XVKecN68mOG7xXCQFEyNlA1bBBf4MkK5v6+JVQgr0dqkiyUPTWYVR7yqRJ784/5XY88a4mQGc wyGc1ayEYiyzEIDIvFxgD71Eql0wyVKiQi4JerFjPVgbo6xEYdnUWw9Q+e2NvuhsnE9ZNxGaD knxLa6G+kLRBgxQQBfpxjB32YnjWz1tioVHEmpi/y+u3AAegQlzcdNs6MR7hgBo4kQ7ojWywC 5xxCOs6+QDZa2R9cIIwHG+AeaxezQhNWwfKidrlYV+zd1b7IpjncM4vljmj1bz6HZpX+JT1H X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-BeenThere: debbugs-submit@debbugs.gnu.org X-Mailman-Version: 2.1.18 Precedence: list X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] X-Received-From: 209.51.188.43 X-BeenThere: bug-gnu-emacs@gnu.org List-Id: "Bug reports for GNU Emacs, the Swiss army knife of text editors" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane.org@gnu.org Original-Sender: "bug-gnu-emacs" Xref: news.gmane.org gmane.emacs.bugs:174290 Archived-At: --egj6aogtrfgv725c Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Content-Transfer-Encoding: quoted-printable I've turned to playing with the emacs calendar and diary, and have several suggestions for its surprisingly good Hebrew support. Attached is an working elisp proof-of-concept. Attach: /home/optimum/Projects/emacs-related/calendar-ivrit/cal-ivrit.el c= al-ivrit.el 1) sunset-awareness. Currently, emacs does warn the user that a Hebrew date being presented is for the period midnight-sunset, but its trivial for emacs to check whether the current time is after sunset and to increment the date accordingly. In such cases, the date is labeled `eve of foo' to make it clear that sunset has been taken into account. 2) Hebrew data in Hebrew. Instead of transliterating Hebrew words into Latin characters, print them in unicode Hebrew. 2.1) This exposed three bugs in the bidi rendering of the diary buffer: A) Hebrew text lines in the diary are rendered left justified. B) Hebrew text lines in the diary are rendered in reverse sequence. C) RTL and LTR lines are rendered out of sequence to each other. 2.1.1) Bug A can be avoided by locally redefining the regexes that identify bidi paragraphs, and I've included that in the attached code. 2.1.2) Bugs B and C may possibly be related to bug #15541. 3) The code includes a generalized function for rendering Hebrew numbers for Hebrew dates, which is an improvement on a function `Footnote-hebrew-numeric' submitted in bug report #29759. There should only be a single function, generically named. 4) Parasha information is presented for the entire week leading up to its Shabbat reading. Currently, it's only displayed on Saturdays. =2D- hkp://keys.gnupg.net CA45 09B5 5351 7C11 A9D1 7286 0036 9E45 1595 8BC0 --egj6aogtrfgv725c Content-Type: text/plain; charset=utf-8 Content-Description: cal-ivrit.el Content-Disposition: attachment; filename="cal-ivrit.el" Content-Transfer-Encoding: quoted-printable ;; cal-ivrit.el --- Hebraized Hebrew calendar and diary -*- coding: utf-8;= -*- ;; =C2=A92020 Boruch Baum , GPL3+, assignable to Free= Software Foundation. ;;; Commentary: ;; This extends the existing Hebrew support of the Emacs calendar ;; (`cal-hebrew.el') and diary. ;; ;; * Hebrew data is presented in Hebrew characters. ;; ;; * Sunset awareness for Hebrew dates. Between sunset and midnight, ;; the Hebrew date is incremented, and the dates Hebrew details ;; displayed accordingy, without affecting the secular date. ;;; Installation: ;; * Refer to the installation instructions for packages `calendar' ;; and `diary'. Notably, variables `calendar-latitude' and ;; `calendar-longitude' must be set to the user's location. ;; * Without the following, when Hebrew text lines exist in the ;; diary, they will appear not only left justified, but also out ;; of sequence with LTR lines! Even, so the RTL lines themselves ;; appear in reverse. (TODO: File a bug report for this. It may be ;; related to a BIDI bug I reported years ago regarding org-mode ;; headings). ;; ;; (add-hook 'diary-fancy-display-mode-hook ;; 'cal-ivrit-diary-fancy-display-mode-hook-function) ;; ;; Here's an example of how to create a template for ;; entries to include Hebrew-related material ;; ;; #+NAME: ~/.emacs.d/diary ;; #+BEGIN_EXAMPLE ;; &%%(cal-ivrit-diary-date) ;; &%%(cal-ivrit-diary-parasha) ;; &%%(cal-ivrit-diary-candles) ;; ;; &%%(diary-hebrew-date) ;; &%%(diary-hebrew-omer) ;; &%%(diary-hebrew-parasha) ;; &%%(diary-hebrew-rosh-hodesh) ;; &%%(diary-hebrew-sabbath-candles) ;; &%%(diary-lunar-phases) ;; &%%(diary-sunrise-sunset) ;; #+END_EXAMPLE ;;; Developer notes: ;; Implementation options: ;; 1) Integrate these functions directly into the current ;; `cal-hebrew.el' equivalents by modifying those functions to ;; branch based upon the value of `calendar-hebrew-in-ivrit'. ;; ;; 2) Create a minor mode `calendar-hebrew-in-ivrit' that advises ;; around the functions of `cal-hebrew.el'. ;; ;; 3) Keep the two packages totally separate. Easiest for the ;; developers and most burdensome for a user intent on switching ;; back and forth. ;; ;; (cond ;; (calendar-hebrew-in-ivrit ;; (advice-add 'calendar-hebrew-date-string :around #'cal-ivrit-date-st= ring)) ;; (advice-add #'cal-ivrit-print-date ;; (t ;; (advice-remove 'calendar-hebrew-date-string #'cal-ivrit-date-string)= )) ;; Code duplication: ;; Variables `hebrew-numeric-regex' and `hebrew-numeric' are ;; duplications of variables `footnote-hebrew-numeric-regex' and ;; `footnote-hebrew-numeric', and function `hebrew-numeric' is ;; basically a duplicate of function `Footnote-hebrew-numeric', the ;; only difference being the option to add single/double ;; apostrophes. Consider refactoring the footnote versions, and ;; moving these to a generic hebrew support elisp file. ;; Advised functions: ;; The option to implement many/most/all/? of the features of this ;; package as advices around existing functions was made in order ;; to make it easy for the user to toggle between this Hebrew ;; language version and the default native language version. The ;; design is that the user need only change the boolean variable ;; `calendar-hebrew-in-ivrit' for this morsel of instant ;; gratification. ;; ;; calendar-hebrew-date-string -> cal-ivrit-date-string ;; diary-hebrew-parasha -> cal-ivrit-diary-parasha (NOT DONE!!) ;;; Code: ; (require 'calendar) ; Redundant. Brought in by `cal-hebrew' (require 'cal-hebrew) ;;; Defcustoms: (defcustom calendar-hebrew-in-ivrit t "Whether to display Hebrew data in Hebrew." :type 'boolean) ;;; Constants: (defconst cal-ivrit-month-name-array-for-common-year ["=D7=A0=D7=99=D7=A1=D7=9F" "=D7=90=D7=99=D7=99=D7=A8" "=D7=A1=D7=99=D7= =95=D7=9F" "=D7=AA=D7=9E=D7=95=D7=96" "=D7=90=D7=91" "=D7=90=D7=9C=D7=95= =D7=9C" "=D7=AA=D7=A9=D7=A8=D7=99" "=D7=97=D7=A9=D7=95=D7=9F" "=D7=9B=D7=A1=D7= =9C=D7=95" "=D7=98=D7=91=D7=AA" "=D7=A9=D7=91=D7=98" "=D7=90=D7=93=D7=A8"= ]) (defconst cal-ivrit-month-name-array-for-leap-year ["=D7=A0=D7=99=D7=A1=D7=9F" "=D7=90=D7=99=D7=99=D7=A8" "=D7=A1=D7=99=D7= =95=D7=9F" "=D7=AA=D7=9E=D7=95=D7=96" "=D7=90=D7=91" "=D7=90=D7=9C=D7=95= =D7=9C" "=D7=AA=D7=A9=D7=A8=D7=99" "=D7=97=D7=A9=D7=95=D7=9F" "=D7=9B=D7=A1=D7= =9C=D7=95" "=D7=98=D7=91=D7=AA" "=D7=A9=D7=91=D7=98" "=D7=90=D7=93=D7=A8= =D7=90" "=D7=90=D7=93=D7=A8 =D7=91"]) (defconst cal-ivrit-day-name-array ["=D7=A8=D7=90=D7=A9=D7=95=D7=9F" "=D7=A9=D7=A0=D7=99" "=D7=A9=D7=9C=D7= =99=D7=A9=D7=99" "=D7=A8=D7=91=D7=99=D7=A2=D7=99" "=D7=97=D7=9E=D7=99=D7= =A9=D7=99" "=D7=A9=D7=99=D7=A9=D7=99" "=D7=A9=D7=91=D7=AA"]) (defconst cal-ivrit-day-name-array-ivrit ["=D7=99=D7=95=D7=9D =D7=90" "=D7=99=D7=95=D7=9D =D7=91" "=D7=99=D7=95= =D7=9D =D7=92" "=D7=99=D7=95=D7=9D =D7=93" "=D7=99=D7=95=D7=9D =D7=94" "= =D7=99=D7=95=D7=9D =D7=95" "=D7=A9=D7=91=D7=AA"]) (defconst cal-ivrit-day-abbrev-array ["=D7=90'" "=D7=91'" "=D7=92'" "=D7=93'" "=D7=94'" "=D7=95'" "=D7=96'"]) (defconst cal-ivrit-day-header-array ["=D7=90" "=D7=91" "=D7=92" "=D7=93" "=D7=94" "=D7=95" "=D7=A9"]) (defconst cal-ivrit-parashiot-names ["=D7=91=D7=A8=D7=90=D7=A9=D7=99=D7=AA" "=D7=A0=D7=95=D7=97" "=D7= =9C=D7=9A =D7=9C=D7=9A" "=D7=95=D7=99=D7=A8=D7=90" "=D7=97=D7=99=D7=99 = =D7=A9=D7=A8=D7=94" "=D7=AA=D7=95=D7=9C=D7=93=D7=95=D7=AA" "=D7=95=D7=99=D7=A6=D7=90" "=D7=95=D7=99=D7=A9=D7=9C=D7=97" "=D7=95= =D7=99=D7=A9=D7=91" "=D7=9E=D7=A7=D7=A5" "=D7=95=D7=99=D7=92=D7=A9" = "=D7=95=D7=99=D7=97=D7=99" "=D7=A9=D7=9E=D7=95=D7=AA" "=D7=95=D7=90=D7=A8=D7=90" "=D7=91= =D7=90" "=D7=91=D7=A9=D7=9C=D7=97" "=D7=99=D7=AA=D7=A8=D7=95" = "=D7=9E=D7=A9=D7=A4=D7=98=D7=99=D7=9D" "=D7=AA=D7=A8=D7=95=D7=9E=D7=94" "=D7=AA=D7=A6=D7=95=D7=94" "=D7=9B= =D7=99 =D7=AA=D7=A9=D7=90" "=D7=95=D7=99=D7=A7=D7=94=D7=9C" "=D7=A4=D7= =A7=D7=95=D7=93=D7=99" "=D7=95=D7=99=D7=A7=D7=A8=D7=90" "=D7=A6=D7=95" "=D7=A9=D7=9E=D7=99=D7=A0=D7=99" "=D7=AA=D7=96= =D7=A8=D7=99=D7=A2" "=D7=9E=D7=A6=D7=95=D7=A8=D7=A2" "=D7=90=D7=97= =D7=A8=D7=99 =D7=9E=D7=95=D7=AA" "=D7=A7=D7=93=D7=95=D7=A9=D7=99=D7=9D" "=D7=90=D7=9E=D7=95=D7=A8" "=D7=91=D7=94=D7=A8" "=D7=91=D7= =97=D7=A7=D7=95=D7=AA=D7=99" "=D7=91=D7=9E=D7=93=D7=91=D7=A8" "=D7=A0=D7= =A9=D7=90" "=D7=91=D7=94=D7=A2=D7=9C=D7=AA=D7=9A" "=D7=A9=D7=9C=D7=97 =D7=9C=D7=9A" "=D7=A7=D7=A8=D7=97" "=D7=97=D7=A7= =D7=AA" "=D7=91=D7=9C=D7=A7" "=D7=A4=D7=A0=D7=97=D7=A1" "=D7= =9E=D7=98=D7=95=D7=AA" "=D7=9E=D7=A1=D7=A2=D7=99" "=D7=93=D7=91=D7=A8=D7=99=D7=9D" "= =D7=95=D7=90=D7=AA=D7=97=D7=A0=D7=9F" "=D7=A2=D7=A7=D7=91" "=D7=A8= =D7=90=D7=94" "=D7=A9=D7=95=D7=A4=D7=98=D7=99=D7=9D" "=D7=9B=D7=99 =D7=AA=D7=A6=D7=90" "=D7=9B=D7=99 =D7=AA=D7=91=D7=95= =D7=90" "=D7=A0=D7=A6=D7=91=D7=99=D7=9D" "=D7=95=D7=99=D7=9C=D7=9A" "= =D7=94=D7=90=D7=96=D7=99=D7=A0=D7=95"] "The names of the parashiot in the Torah, in Hebrew.") (defconst cal-ivrit--jm-lat 31.77 "Lattitude for Jerusalem") (defconst cal-ivrit--jm-long 35.22 "Lattitude for Jerusalem") ;;; Generic Hebrew utility constants and functions (defconst hebrew-numeric-regex "[=D7=90=D7=91=D7=92=D7=93=D7=94=D7=95=D7= =96=D7=97=D7=98=D7=99=D7=9B=D7=9C=D7=9E=D7=A0=D7=A1=D7=A2=D7=A4=D7=A6=D7= =A7=D7=A8=D7=A9=D7=AA']+") ; (defconst hebrew-numeric-regex "\\([=D7=90=D7=91=D7=92=D7=93=D7=94=D7=95= =D7=96=D7=97=D7=98]'\\)?\\(=D7=AA\\)?\\(=D7=AA\\)?\\([=D7=A7=D7=A8=D7=A9= =D7=AA]\\)?\\([=D7=98=D7=99=D7=9B=D7=9C=D7=9E=D7=A0=D7=A1=D7=A2=D7=A4=D7= =A6]\\)?\\([=D7=90=D7=91=D7=92=D7=93=D7=94=D7=95=D7=96=D7=97=D7=98]\\)?") (defconst hebrew-numeric '( ("=D7=90" "=D7=91" "=D7=92" "=D7=93" "=D7=94" "=D7=95" "=D7=96" "=D7=97"= "=D7=98") ("=D7=99" "=D7=9B" "=D7=9C" "=D7=9E" "=D7=A0" "=D7=A1" "=D7=A2" "=D7=A4"= "=D7=A6") ("=D7=A7" "=D7=A8" "=D7=A9" "=D7=AA" "=D7=AA=D7=A7" "=D7=AA=D7=A8"" =D7= =AA=D7=A9" "=D7=AA=D7=AA" "=D7=AA=D7=AA=D7=A7"))) ;;;###cal-autoload (defun hebrew-numeric(n &optional quote) "Convert a base 10 Western number to it Hebrew character equivalent. With QUOTE non-nil, include customary single or double quotes." (let* ((quote (if quote "'" "")) (n (+ (mod n 10000) (/ n 10000))) (thousands (/ n 1000)) (hundreds (/ (mod n 1000) 100)) (tens (/ (mod n 100) 10)) (units (mod n 10)) (special (if (not (=3D tens 1)) nil (or (when (=3D units 5) "=D7=98=D7=95") (when (=3D units 6) "=D7=98=D7=96")))) (result (concat (when (/=3D 0 thousands) (concat (nth (1- thousands) (nth 0 hebre= w-numeric)) quote)) (when (/=3D 0 hundreds) (nth (1- hundreds) (nth 2 hebrew-numeric)= )) (if special special (concat (when (/=3D 0 tens) (nth (1- tens) (nth 1 hebrew-numeric))) (when (/=3D 0 units) (nth (1- units) (nth 0 hebrew-numeric))))= )))) (cond ((=3D 1 (length result)) (concat result quote)) ((string-match "'" result -2) result) (t (concat (substring result 0 -1) (if quote "\"" "") (substring result = -1)))))) ;; Calendar functions ;; ;;;###cal-autoload ;; (defun cal-ivrit-location-checking () ;; "Use Jerusalem if the system coordinates are invalid." ;; (message "Boruch 1") ;; (when (or (not calendar-latitude) ;; (> calendar-latitude 90) ;; (< calendar-latitude -90) ;; (not calendar-longitude) ;; (> calendar-longitude 180) ;; (< calendar-longitude -180)) ;; (lwarn 'calendar-hebrew ":warning" ;; "Invalid calendar-lattitude/longitude %d/%d" ;; calendar-latitude calendar-longitude) ;; (message "Boruch 2") ;; (make-local-variable 'calendar-latitude) ;; (make-local-variable 'calendar-longitude) ;; (make-local-variable 'calendar-location-name) ;; (setq calendar-latitude cal-ivrit--jm-lat) ;; (setq calendar-longitude cal-ivrit--jm-long) ;; (setq calendar-location-name "=D7=99=D7=A8=D7=95=D7=A9=D7=9C=D7=99= =D7=9D"))) ;; ;; Um. This doesn't seem the right way to do this... ;; (add-hook 'calendar-mode-hook 'cal-ivrit-location-checking) ;; (add-hook 'diary-fancy-display-mode-hook 'cal-ivrit-location-checking) ;; ;; And, it doesn't work! ;; ;; + calendar calls solar.. before running the hook, so nil's cause an = error/crash ;;;###cal-autoload (defun cal-ivrit-date-string (&optional orig-fun date) "Display a Hebrew date in a native Hebrew format. The ORIG-FUN argument exists to allow this function to be advised around function `calendar-hebrew-date-string'. If DATE is nil, the current date is assumed. Note that the native Hebrew format will often differ from `calendar-date-display-form'." ;; Programming note: The code here is an adaptation of functions ;; `calendar-hebrew-date-string' and `calendar-date-string'. (if (not calendar-hebrew-in-ivrit) (apply orig-fun date) (let* ((this-date (copy-tree (or date (calendar-current-date)))) (eve (if (not (equal this-date (calendar-current-date))) "" (let ((sunset (caadr (solar-sunrise-sunset (calendar-current= -date)))) (hour (string-to-number(format-time-string "%H")))) (if (and sunset (or (> hour (truncate sunset)) (and (=3D (truncate sunset) hour) (> (string-to-number (format-time-string= "%M") ) (truncate (* 60 (mod sunset 1))))))) (and (incf (nth 1 this-date)) "=D7=9C=D7=99=D7=9C ") ; alternatively: "=D7=90=D7= =95=D7=A8 =D7=9C=D7=99=D7=95=D7=9D " ; English: "eve of" "")))) (hebrew-date (calendar-hebrew-from-absolute (calendar-absolute-from-gregorian this-date))) (calendar-month-name-array (if (calendar-hebrew-leap-year-p (calendar-extract-year hebrew-da= te)) cal-ivrit-month-name-array-for-leap-year cal-ivrit-month-name-array-for-common-year)) (calendar-day-name-array cal-ivrit-day-name-array-ivrit) (calendar-day-abbrev-array cal-ivrit-day-abbrev-array) (calendar-day-header-array cal-ivrit-day-header-array) ;; `abbreviate' and `nodayname' are optional args for function ;; `calendar-date-string'. Consider allowing those options ;; here, but for now hard-code defaults. (abbreviate nil) (nodayname t) (dayname (unless nodayname (calendar-day-name hebrew-date))) (month (calendar-extract-month hebrew-date)) (monthname (calendar-month-name month abbreviate)) (day (hebrew-numeric (calendar-extract-day hebrew-date) t)) (month (hebrew-numeric month t)) (year (substring (hebrew-numeric (calendar-extract-year hebrew-dat= e) t) 2))) (concat eve (when dayname (concat dayname ", ")) day " " monthname ", " year)))) ;;;###cal-autoload (defun cal-ivrit-parasha-name (p) "Name(s) corresponding to parasha P." (if (arrayp p) ; combined parasha (format "%s/%s" (aref cal-ivrit-parashiot-names (aref p 0)) (aref cal-ivrit-parashiot-names (aref p 1))) (aref cal-ivrit-parashiot-names p))) ;;;###cal-autoload (defun cal-ivrit-print-date () "Display in the echo area the Hebrew date at the cursor position." (interactive) (message "=D7=AA=D7=90=D7=A8=D7=99=D7=9A: %s" (cal-ivrit-date-string nil (calendar-cursor-to-date t)))) ;;; Diary functions ;; To be called from diary-list-sexp-entries, where DATE is bound. ;;;###diary-autoload (defun cal-ivrit-diary-date () "Hebrew calendar equivalent of date diary entry, in Hebrew." ;; Note the leading space (See commentary/developer notes/RTL) (format " =D7=AA=D7=90=D7=A8=D7=99=D7=9A: %s" (cal-ivrit-date-string nil= date))) ;; To be called from diary-list-sexp-entries, where DATE is bound. ;;;###diary-autoload (defun cal-ivrit-diary-parasha (&optional mark) "Fancy diary entry for the Hebrew parasha, in Hebrew. An optional parameter MARK specifies a face or single-character string to use when highlighting the day in the calendar. Note that unlike `diary-hebrew-parasha', this function displays a Parasha name every day of the week." (let* ((d (calendar-absolute-from-gregorian (or date (calendar-current-d= ate)))) (shabbat (if (=3D (% d 7) 6) "" (setq d (+ d 7)) " =D7=A9=D7=91=D7=AA")) (h-year (calendar-extract-year (calendar-hebrew-from-absolute d))) (rosh-hashanah (calendar-hebrew-to-absolute (list 7 1 h-year))) (passover (calendar-hebrew-to-absolute (list 1 15 h-year))) (rosh-hashanah-day (aref calendar-day-name-array (% rosh-hashanah 7))) (passover-day (aref calendar-day-name-array (% passover 7))) (long-h (calendar-hebrew-long-heshvan-p h-year)) (short-k (calendar-hebrew-short-kislev-p h-year)) (type (cond ((and long-h (not short-k)) "complete") ((and (not long-h) short-k) "incomplete") (t "regular"))) (year-format (symbol-value (intern (format "calendar-hebrew-year-%s-%s-%s" ; keviah rosh-hashanah-day type passover-day)))) (first-saturday ; of Hebrew year (calendar-dayname-on-or-before 6 (+ 6 rosh-hashanah))) (saturday ; which Saturday of the Hebrew year (/ (- d first-saturday) 7)) (parasha (aref year-format saturday))) (if parasha (cons mark (format ;; Note the leading space (See commentary/developer notes/RTL= ) "%s =D7=A4=D7=A8=D7=A9=D7=AA %s" shabbat (if (listp parasha) ; Israel differs from diaspora (if (car parasha) (format "%s (=D7=97=D7=95\"=D7=9C), %s (=D7=90\"=D7= =99)" (cal-ivrit-parasha-name (car parasha)) (cal-ivrit-parasha-name (cdr parasha))) (format "%s (=D7=90\"=D7=99)" (cal-ivrit-parasha-name (cdr parasha)))) (cal-ivrit-parasha-name parasha))))))) ;; To be called from diary-list-sexp-entries, where DATE is bound. ;;;###diary-autoload (defun cal-ivrit-diary-candles (&optional mark) "Diary entry for candle lighting time on Sabbath and Holiday eves. No diary entry if there is no sunset on that date. Uses `diary-hebrew-sabbath-candles-minutes'. An optional parameter MARK specifies a face or single-character string to use when highlighting the day in the calendar." (require 'solar) (or (and calendar-latitude calendar-longitude calendar-time-zone) (solar-setup)) (if (=3D (% (calendar-absolute-from-gregorian date) 7) 5) ; Friday (let ((sunset (cadr (solar-sunrise-sunset date)))) (if sunset (cons mark (format " =D7=94=D7=93=D7=9C=D7=A7=D7=AA =D7=A0=D7=A8=D7= =95=D7=AA: %s" (apply 'solar-time-string (cons (- (car sunset) (/ diary-hebrew-sabbath-candles-mi= nutes 60.0)) (cdr sunset))))))))) ;;;###diary-autoload (defun cal-ivrit-diary-fancy-display-mode-hook-function () (setq bidi-paragraph-start-re "^") (setq bidi-paragraph-separate-re "^")) ;; TODO: ;; ;; + cal-ivrit-diary-candles ;; + erev chag ;; + second-day yom-tov / Sunday yom-tov ;;+ todo for hebraization: ;; (diary-lunar-phases) ;; (diary-hebrew-omer) ;; (diary-hebrew-rosh-hodesh) ;; (diary-sunrise-sunset) (provide 'cal-ivrit) ;;; cal-ivrit.el ends here --egj6aogtrfgv725c--