Merge from vendor branch READLINE:
[dragonfly.git] / games / piano / piano.c
1 /*
2  * piano.c - a piano emulator
3  *
4  * $FreeBSD: src/games/piano/piano.c,v 1.7 1999/12/12 03:22:37 billf Exp $
5  * $DragonFly: src/games/piano/piano.c,v 1.2 2003/06/17 04:25:24 dillon Exp $
6  */
7 #include <stdio.h>
8 #include <stdlib.h>
9 #include <string.h>
10 #include <curses.h>
11
12 #include <unistd.h>
13 #include <sys/file.h>
14
15 char *myname;
16 int verbose;
17 static char *initcmd = "t160 o1 l16 ml";
18
19 static char usage_msg[] =
20         "simple keyboard player V0.8086\n"
21         "usage: %s [-v][-i str]\n"
22         "\t-i str defaults 't160 o1 l16 ml'\n"
23         "function: play by console keyboard\n"
24         "\tESC to exit. Note keys are ...\n"
25         "\t1 2   4 5   7 8 9   - = \\\n"
26         "\t Q W E R T Y U I O P [ ]\n"
27         ;
28
29 struct kdef_t {
30         int ch;
31         char *str;
32 };
33
34 static char *kstr[256];
35
36 static struct kdef_t kdef[] = {
37         /* white key */
38         { '\t', "<g>" },
39         { 'q', "<a>" },
40         { 'w', "<b>" },
41         { 'e', "c" },
42         { 'r', "d" },
43         { 't', "e" },
44         { 'y', "f" },
45         { 'u', "g" },
46         { 'i', "a" },
47         { 'o', "b" },
48         { 'p', ">c<" },
49         { '[', ">d<" },
50         { ']', ">e<" },
51         { '\n', ">f<" },
52         { '\r', ">f<" },
53         /* black key */
54         { '`', "<f#>" },
55         { '1', "<g#>" },
56         { '2', "<a#>" },
57         /*{ '3', "<b#>" },*/
58         { '4', "c#" },
59         { '5', "d#" },
60         /*{ '6', "e#" },*/
61         { '7', "f#" },
62         { '8', "g#" },
63         { '9', "a#" },
64         /*{ '0', "b#" },*/
65         { '-', ">c#<" },
66         { '=', ">d#<" },
67         /*{ '\', ">e#<" },*/
68         { '\177', ">f#<" },
69         { '\0', NULL }
70 };
71
72 static int
73 init_kstr(void)
74 {
75         struct kdef_t *mv = kdef;
76         while (mv->str != NULL) {
77                 kstr[mv->ch] = mv->str;
78                 mv++;
79         }/* while */
80         return 0;
81 }/* init_kstr */
82
83 static int
84 fdputs(const char *s, int fd, int echo)
85 {
86         int err, len = strlen(s);
87         write(fd, s, len);
88         err = write(fd, "\n", 1);
89         if (echo) {
90                 fputs(s, stdout);
91         }
92         return err;
93 }/* fdputs */
94
95 static int
96 outspkr(const char *s)
97 {
98         int err = -1, fd = open("/dev/speaker", O_WRONLY);
99         if (fd >= 0) {
100                 fdputs(initcmd, fd, 0);
101                 err = fdputs(s, fd, verbose);
102                 close(fd);
103         }
104         return err;
105 }/* outspkr */
106
107 static int
108 nain(void)
109 {
110         int ch;
111         initscr();
112         noecho();
113         nonl();
114         raw();
115         init_kstr();
116         while ((ch = getch()) != '\033') {
117                 if (kstr[ch] != NULL) {
118                         outspkr(kstr[ch]);
119                 }
120                 else {
121                         if (verbose) {
122                                 switch (ch) {
123                                 case ' ':
124                                         fputs(" ", stdout);
125                                         break;
126                                 case '\b':
127                                         fputs("\b", stdout);
128                                         break;
129                                 }/* switch */
130                         }
131                 }
132         }/* while */
133         endwin();
134         return 0;
135 }/* nain */
136
137 int
138 main(int argc, char *argv[])
139 {
140         int ch, ex, show_usage = 0;
141         myname = argv[0];
142         while ((ch = getopt(argc, argv, "-vi:")) != -1) {
143                 switch (ch) {
144                 default:
145                 case 'V':
146                         show_usage++;
147                         break;
148                 case 'v':
149                         verbose++;
150                         break;
151                 case 'i':
152                         initcmd = optarg;
153                         break;
154                 }/* switch */
155         }/* while */
156         ex = 1;
157         if (show_usage) {
158                 fprintf(stderr, usage_msg, myname);
159         }
160         else {
161                 printf("Type ESC to exit.\n");
162                 ex = 0;
163                 nain();
164         }
165         return ex;
166 }/* main */