ncurses 4.2
[ncurses.git] / ncurses / lib_options.c
1 /****************************************************************************
2  * Copyright (c) 1998 Free Software Foundation, Inc.                        *
3  *                                                                          *
4  * Permission is hereby granted, free of charge, to any person obtaining a  *
5  * copy of this software and associated documentation files (the            *
6  * "Software"), to deal in the Software without restriction, including      *
7  * without limitation the rights to use, copy, modify, merge, publish,      *
8  * distribute, distribute with modifications, sublicense, and/or sell       *
9  * copies of the Software, and to permit persons to whom the Software is    *
10  * furnished to do so, subject to the following conditions:                 *
11  *                                                                          *
12  * The above copyright notice and this permission notice shall be included  *
13  * in all copies or substantial portions of the Software.                   *
14  *                                                                          *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS  *
16  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF               *
17  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.   *
18  * IN NO EVENT SHALL THE ABOVE COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,   *
19  * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR    *
20  * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR    *
21  * THE USE OR OTHER DEALINGS IN THE SOFTWARE.                               *
22  *                                                                          *
23  * Except as contained in this notice, the name(s) of the above copyright   *
24  * holders shall not be used in advertising or otherwise to promote the     *
25  * sale, use or other dealings in this Software without prior written       *
26  * authorization.                                                           *
27  ****************************************************************************/
28
29 /****************************************************************************
30  *  Author: Zeyd M. Ben-Halim <zmbenhal@netcom.com> 1992,1995               *
31  *     and: Eric S. Raymond <esr@snark.thyrsus.com>                         *
32  ****************************************************************************/
33
34
35 /*
36 **      lib_options.c
37 **
38 **      The routines to handle option setting.
39 **
40 */
41
42 #include <curses.priv.h>
43
44 #include <term.h>       /* keypad_xmit, keypad_local, meta_on, meta_off */
45                         /* cursor_visible,cursor_normal,cursor_invisible */
46
47 MODULE_ID("$Id: lib_options.c,v 1.29 1998/02/11 12:13:55 tom Exp $")
48
49 int has_ic(void)
50 {
51         T((T_CALLED("has_ic()")));
52         returnCode((insert_character || parm_ich
53            ||  (enter_insert_mode && exit_insert_mode))
54            &&  (delete_character || parm_dch));
55 }
56
57 int has_il(void)
58 {
59         T((T_CALLED("has_il()")));
60         returnCode((insert_line || parm_insert_line)
61                 && (delete_line || parm_delete_line));
62 }
63
64 int idlok(WINDOW *win,  bool flag)
65 {
66         T((T_CALLED("idlok(%p,%d)"), win, flag));
67
68         if (win) {
69           _nc_idlok = win->_idlok = flag && (has_il() || change_scroll_region);
70           returnCode(OK);
71         }
72         else
73           returnCode(ERR);
74 }
75
76
77 void idcok(WINDOW *win, bool flag)
78 {
79         T((T_CALLED("idcok(%p,%d)"), win, flag));
80
81         if (win)
82           _nc_idcok = win->_idcok = flag && has_ic();
83
84         returnVoid;
85 }
86
87 int halfdelay(int t)
88 {
89         T((T_CALLED("halfdelay(%d)"), t));
90
91         if (t < 1 || t > 255)
92                 returnCode(ERR);
93
94         cbreak();
95         SP->_cbreak = t+1;
96         returnCode(OK);
97 }
98
99 int nodelay(WINDOW *win, bool flag)
100 {
101         T((T_CALLED("nodelay(%p,%d)"), win, flag));
102
103         if (win) {
104           if (flag == TRUE)
105             win->_delay = 0;
106           else win->_delay = -1;
107           returnCode(OK);
108         }
109         else
110           returnCode(ERR);
111 }
112
113 int notimeout(WINDOW *win, bool f)
114 {
115         T((T_CALLED("notimout(%p,%d)"), win, f));
116
117         if (win) {
118           win->_notimeout = f;
119           returnCode(OK);
120         }
121         else
122           returnCode(ERR);
123 }
124
125 int wtimeout(WINDOW *win, int delay)
126 {
127         T((T_CALLED("wtimeout(%p,%d)"), win, delay));
128
129         if (win) {
130           win->_delay = delay;
131           returnCode(OK);
132         }
133         else
134           returnCode(ERR);
135 }
136
137 int keypad(WINDOW *win, bool flag)
138 {
139         T((T_CALLED("keypad(%p,%d)"), win, flag));
140
141         if (win) {
142           win->_use_keypad = flag;
143           returnCode(_nc_keypad(flag));
144         }
145         else
146           returnCode(ERR);
147 }
148
149
150 int meta(WINDOW *win GCC_UNUSED, bool flag)
151 {
152         /* Ok, we stay relaxed and don't signal an error if win is NULL */
153         T((T_CALLED("meta(%p,%d)"), win, flag));
154
155         SP->_use_meta = flag;
156
157         if (flag  &&  meta_on)
158         {
159             TPUTS_TRACE("meta_on");
160             putp(meta_on);
161         }
162         else if (! flag  &&  meta_off)
163         {
164             TPUTS_TRACE("meta_off");
165             putp(meta_off);
166         }
167         returnCode(OK);
168 }
169
170 /* curs_set() moved here to narrow the kernel interface */
171
172 int curs_set(int vis)
173 {
174 int cursor = SP->_cursor;
175
176         T((T_CALLED("curs_set(%d)"), vis));
177
178         if (vis < 0 || vis > 2)
179                 returnCode(ERR);
180
181         if (vis == cursor)
182                 returnCode(cursor);
183
184         switch(vis) {
185         case 2:
186                 if (cursor_visible)
187                 {
188                         TPUTS_TRACE("cursor_visible");
189                         putp(cursor_visible);
190                 }
191                 else
192                         returnCode(ERR);
193                 break;
194         case 1:
195                 if (cursor_normal)
196                 {
197                         TPUTS_TRACE("cursor_normal");
198                         putp(cursor_normal);
199                 }
200                 else
201                         returnCode(ERR);
202                 break;
203         case 0:
204                 if (cursor_invisible)
205                 {
206                         TPUTS_TRACE("cursor_invisible");
207                         putp(cursor_invisible);
208                 }
209                 else
210                         returnCode(ERR);
211                 break;
212         }
213         SP->_cursor = vis;
214         (void) fflush(SP->_ofp);
215
216         returnCode(cursor==-1 ? 1 : cursor);
217 }
218
219 int typeahead(int fd)
220 {
221         T((T_CALLED("typeahead(%d)"), fd));
222         SP->_checkfd = fd;
223         returnCode(OK);
224 }
225
226 /*
227 **      has_key()
228 **
229 **      Return TRUE if the current terminal has the given key
230 **
231 */
232
233
234 static int has_key_internal(int keycode, struct tries *tp)
235 {
236     if (tp == 0)
237         return(FALSE);
238     else if (tp->value == keycode)
239         return(TRUE);
240     else
241         return(has_key_internal(keycode, tp->child)
242                || has_key_internal(keycode, tp->sibling));
243 }
244
245 int has_key(int keycode)
246 {
247     T((T_CALLED("has_key(%d)"), keycode));
248     returnCode(has_key_internal(keycode, SP->_keytry));
249 }
250
251 /*
252 **      init_keytry()
253 **
254 **      Construct the try for the current terminal's keypad keys.
255 **
256 */
257
258 static void init_keytry(void)
259 {
260 /* LINT_PREPRO
261 #if 0*/
262 #include <keys.tries>
263 /* LINT_PREPRO
264 #endif*/
265         size_t n;
266
267         /* The SP->_keytry value is initialized in newterm(), where the SP
268          * structure is created, because we can not tell where keypad() or
269          * mouse_activate() (which will call keyok()) are first called.
270          */
271
272         for (n = 0; n < SIZEOF(table); n++)
273                 if (table[n].offset < STRCOUNT)
274                 _nc_add_to_try(&(SP->_keytry),
275                         CUR Strings[table[n].offset],
276                         table[n].code);
277 }
278
279 /* Turn the keypad on/off
280  *
281  * Note:  we flush the output because changing this mode causes some terminals
282  * to emit different escape sequences for cursor and keypad keys.  If we don't
283  * flush, then the next wgetch may get the escape sequence that corresponds to
284  * the terminal state _before_ switching modes.
285  */
286 int _nc_keypad(bool flag)
287 {
288         if (flag  &&  keypad_xmit)
289         {
290             TPUTS_TRACE("keypad_xmit");
291             putp(keypad_xmit);
292             (void) fflush(SP->_ofp);
293         }
294         else if (! flag  &&  keypad_local)
295         {
296             TPUTS_TRACE("keypad_local");
297             putp(keypad_local);
298             (void) fflush(SP->_ofp);
299         }
300
301         if (!SP->_tried) {
302             init_keytry();
303             SP->_tried = TRUE;
304         }
305         return(OK);
306 }