]> code.delx.au - gnu-emacs-elpa/blob - chess-sound.el
*** no comment ***
[gnu-emacs-elpa] / chess-sound.el
1 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2 ;;
3 ;; This is very similar to chess-announce, except it uses specific
4 ;; .WAV files instead of text-to-speech.
5 ;;
6 ;; $Revision$
7
8 (require 'chess-game)
9
10 (defgroup chess-sound nil
11 "Code to play specific sounds when announcing chess moves."
12 :group 'chess)
13
14 (defcustom chess-sound-directory
15 (expand-file-name "sounds"
16 (file-name-directory
17 (or load-file-name buffer-file-name)))
18 "The directory where chess sounds can be found."
19 :type 'directory
20 :group 'chess-sound)
21
22 (defcustom chess-sound-play-function (if (fboundp 'play-sound-file)
23 'play-sound-file
24 'chess-sound-play)
25 "Non-nil if chess-sound should play sounds ."
26 :type 'file
27 :group 'chess-sound)
28
29 (defcustom chess-sound-program (or (executable-find "esdplay")
30 (executable-find "play"))
31 "Program used to play sounds, if `play-sound-file' does not exist."
32 :type 'file
33 :group 'chess-sound)
34
35 (defcustom chess-sound-args nil
36 "Additional args to pass to `chess-sound-program', before the .WAV file."
37 :type '(repeat string)
38 :group 'chess-sound)
39
40 (defun chess-sound-available-p ()
41 (and (file-directory-p chess-sound-directory)
42 (file-readable-p (expand-file-name "tap.wav"
43 chess-sound-directory))
44 (or (eq chess-sound-play-function 'play-sound-file)
45 (file-executable-p chess-sound-program))))
46
47 (defun chess-sound-for-game (game)
48 "Announce the opponent's moves in GAME."
49 (chess-game-add-hook game 'chess-sound-event-handler))
50
51 (defun chess-sound (ch)
52 (let ((file
53 (cond
54 ((stringp ch)
55 (format "%s.wav" ch))
56 ((memq ch '(?\# ?\+ ?k ?q ?b ?n ?r ?p ?x))
57 (format "%c_.wav" ch))
58 (t
59 (format "%s.wav" (chess-index-to-coord ch))))))
60 (funcall chess-sound-play-function
61 (expand-file-name file chess-sound-directory))))
62
63 (defun chess-sound-play (file)
64 (apply 'call-process chess-sound-program nil nil nil chess-sound-args))
65
66 (defun chess-sound-event-handler (game ignore event &rest args)
67 "This display module presents a standard chessboard.
68 See `chess-display-type' for the different kinds of displays."
69 (cond
70 ((eq event 'move)
71 (let* ((ply (chess-game-ply game (1- (chess-game-index game))))
72 (pos (chess-ply-pos ply)))
73 (if (eq (chess-game-data game 'my-color)
74 (chess-pos-side-to-move pos))
75 (chess-sound "tap")
76 (let* ((source (chess-ply-source ply))
77 (target (chess-ply-target ply))
78 (s-piece (chess-pos-piece pos source))
79 (t-piece (chess-pos-piece pos target))
80 text)
81 (cond
82 ((chess-ply-has-keyword :castle)
83 (chess-sound "O-O"))
84 ((chess-ply-has-keyword :long-castle)
85 (chess-sound "O-O-O"))
86 ((= t-piece ? )
87 (chess-sound (downcase s-piece))
88 (chess-sound target))
89 (t
90 (chess-sound (downcase s-piece))
91 (chess-sound ?x)
92 (chess-sound (downcase t-piece))
93 (chess-sound target)))
94 (if (chess-ply-has-keyword :check)
95 (chess-sound ?+))
96 (if (chess-ply-has-keyword :checkmate)
97 (chess-sound ?#))
98 (if (chess-ply-has-keyword :stalemate)
99 (chess-sound "smate")))))
100 nil)))
101
102 (provide 'chess-sound)
103
104 ;;; chess-sound.el ends here