- Fix KiDispatchException to unmask KI_EXCEPTION_INTERNAL when setting the exception...
[reactos.git] / rosapps / mc / src / win.c
1 /* Curses utilities
2 Copyright (C) 1995 Miguel de Icaza, Janne Kukonlehto
3
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
17
18 #include <config.h>
19 #include "tty.h"
20 #include <stdio.h>
21 #include <stdlib.h> /* For free() */
22 #include <string.h>
23 #if (!defined(__IBMC__) && !defined(__IBMCPP__)) && !defined(OS2_NT)
24 # include <termios.h>
25 #endif
26 #include "mad.h"
27 #include "color.h"
28 #include "mouse.h"
29 #include "util.h" /* For xmalloc() */
30
31 #include "dlg.h"
32 #include "widget.h"
33 #include "win.h"
34 #include "key.h" /* XCTRL and ALT macros */
35 #include "layout.h"
36 #include "global.h"
37
38 /* "$Id$" */
39
40 typedef void (*fnptr)(void);
41
42 typedef struct Fkey_Table_List {
43 fnptr actions[11];
44 struct Fkey_Table_List *next;
45 int has_labels;
46 } Fkey_Table_List;
47
48 static Fkey_Table_List *fkey_table_list = NULL;
49
50 /* Width of output is always seven characters */
51 void sprint_bytesize (char *buffer, int size, int scale)
52 {
53 char scales[] = " kMGT";
54
55 if (size > 0){
56 while (size > 9999 && scale < sizeof (scales)){
57 size = (size + 512) / 1024;
58 scale ++;
59 }
60 }
61 if (scale > 0)
62 sprintf (buffer, "%4d %cb", size, scales[scale]);
63 else
64 sprintf (buffer, "%4d b ", size);
65 }
66
67 void print_bytesize (int size, int scale)
68 {
69 char buffer [10];
70
71 sprint_bytesize (buffer, size, scale);
72 printw (buffer);
73 }
74
75 /* Return values: 0 = not a fkey, other = was a fkey */
76 int check_fkeys (int c)
77 {
78 int fkey;
79
80 if (!fkey_table_list)
81 return 0;
82
83 switch (c){
84 case KEY_F(1):
85 fkey = 1;
86 break;
87 case KEY_F(2):
88 fkey = 2;
89 break;
90 case KEY_F(3):
91 fkey = 3;
92 break;
93 case KEY_F(4):
94 fkey = 4;
95 break;
96 case KEY_F(5):
97 fkey = 5;
98 break;
99 case KEY_F(6):
100 fkey = 6;
101 break;
102 case KEY_F(7):
103 fkey = 7;
104 break;
105 case KEY_F(8):
106 fkey = 8;
107 break;
108 case KEY_F(9):
109 fkey = 9;
110 break;
111 case KEY_F(10):
112 fkey = 10;
113 break;
114 default:
115 return 0;
116 }
117 if (fkey_table_list->actions [fkey]){
118 fkey_table_list->actions [fkey] ();
119 return fkey;
120 }
121 else
122 return 0;
123 }
124
125 /* Return values: 0 = not a movement key, 1 = was a movement key */
126 int check_movement_keys (int c, int additional, int page_size, void *data,
127 movefn backfn, movefn forfn, movefn topfn,
128 movefn bottomfn)
129 {
130 switch (c){
131 case KEY_UP:
132 case XCTRL ('p'):
133 (*backfn)(data, 1);
134 return 1;
135
136 case KEY_DOWN:
137 case XCTRL ('n'):
138 (*forfn)(data, 1);
139 return 1;
140
141 case KEY_PPAGE:
142 case ALT('v'):
143 (*backfn)(data, page_size-1);
144 return 1;
145
146 case KEY_NPAGE:
147 case XCTRL('v'):
148 (*forfn)(data, page_size-1);
149 return 1;
150
151 case KEY_HOME:
152 case KEY_A1:
153 (*topfn)(data, 0);
154 return 1;
155 case KEY_END:
156 case KEY_C1:
157 (*bottomfn)(data, 0);
158 return 1;
159 }
160 if (additional)
161 switch (c){
162 case 'b':
163 case XCTRL('h'):
164 case KEY_BACKSPACE:
165 case 0177:
166 (*backfn)(data, page_size-1);
167 return 1;
168 case ' ':
169 (*forfn)(data, page_size-1);
170 return 1;
171 case 'u':
172 (*backfn)(data, page_size / 2);
173 return 1;
174 case 'd':
175 (*forfn)(data, page_size / 2);
176 return 1;
177 case 'g':
178 (*topfn)(data, 0);
179 return 1;
180 case 'G':
181 (*bottomfn)(data, 0);
182 return 1;
183 }
184 return 0;
185 }
186
187 void mc_raw_mode (void)
188 {
189 raw ();
190 }
191
192 void mc_noraw_mode (void)
193 {
194 noraw ();
195 }
196
197 /* Classification routines */
198 int is_abort_char (int c)
199 {
200 return (c == XCTRL('c') || c == XCTRL('g') || c == ESC_CHAR ||
201 c == KEY_F(10));
202 }
203
204 int is_quit_char (int c)
205 {
206 return (c == XCTRL('g') || (c == ESC_CHAR) || (c == KEY_F(10)));
207 }
208
209 /* This table is a mapping between names and the constants we use
210 * We use this to allow users to define alternate definitions for
211 * certain keys that may be missing from the terminal database
212 */
213 key_code_name_t key_name_conv_tab [] = {
214 /* KEY_F(0) is not here, since we are mapping it to f10, so there is no reason
215 to define f0 as well. Also, it makes Learn keys a bunch of problems :( */
216 { KEY_F(1), "f1", N_("Function key 1") },
217 { KEY_F(2), "f2", N_("Function key 2") },
218 { KEY_F(3), "f3", N_("Function key 3") },
219 { KEY_F(4), "f4", N_("Function key 4") },
220 { KEY_F(5), "f5", N_("Function key 5") },
221 { KEY_F(6), "f6", N_("Function key 6") },
222 { KEY_F(7), "f7", N_("Function key 7") },
223 { KEY_F(8), "f8", N_("Function key 8") },
224 { KEY_F(9), "f9", N_("Function key 9") },
225 { KEY_F(10), "f10", N_("Function key 10") },
226 { KEY_F(11), "f11", N_("Function key 11") },
227 { KEY_F(12), "f12", N_("Function key 12") },
228 { KEY_F(13), "f13", N_("Function key 13") },
229 { KEY_F(14), "f14", N_("Function key 14") },
230 { KEY_F(15), "f15", N_("Function key 15") },
231 { KEY_F(16), "f16", N_("Function key 16") },
232 { KEY_F(17), "f17", N_("Function key 17") },
233 { KEY_F(18), "f18", N_("Function key 18") },
234 { KEY_F(19), "f19", N_("Function key 19") },
235 { KEY_F(20), "f20", N_("Function key 20") },
236 { KEY_BACKSPACE, "bs", N_("Backspace key") },
237 { KEY_END, "end", N_("End key") },
238 { KEY_UP, "up", N_("Up arrow key") },
239 { KEY_DOWN, "down", N_("Down arrow key") },
240 { KEY_LEFT, "left", N_("Left arrow key") },
241 { KEY_RIGHT, "right", N_("Right arrow key") },
242 { KEY_HOME, "home", N_("Home key") },
243 { KEY_NPAGE, "pgdn", N_("Page Down key") },
244 { KEY_PPAGE, "pgup", N_("Page Up key") },
245 { KEY_IC, "insert", N_("Insert key") },
246 { KEY_DC, "delete", N_("Delete key") },
247 { ALT('\t'), "complete", N_("Completion/M-tab") },
248 { KEY_KP_ADD, "kpplus", N_("+ on keypad") },
249 { KEY_KP_SUBTRACT,"kpminus", N_("- on keypad") },
250 { KEY_KP_MULTIPLY,"kpasterix", N_("* on keypad") },
251 /* From here on, these won't be shown in Learn keys (no space) */
252 { KEY_LEFT, "kpleft", N_("Left arrow keypad") },
253 { KEY_RIGHT, "kpright", N_("Right arrow keypad") },
254 { KEY_UP, "kpup", N_("Up arrow keypad") },
255 { KEY_DOWN, "kpdown", N_("Down arrow keypad") },
256 { KEY_HOME, "kphome", N_("Home on keypad") },
257 { KEY_END, "kpend", N_("End on keypad") },
258 { KEY_NPAGE, "kpnpage", N_("Page Down keypad") },
259 { KEY_PPAGE, "kpppage", N_("Page Up keypad") },
260 { KEY_IC, "kpinsert", N_("Insert on keypad") },
261 { KEY_DC, "kpdelete", N_("Delete on keypad") },
262 { (int) '\n', "kpenter", N_("Enter on keypad") },
263 { (int) '/', "kpslash", N_("Slash on keypad") },
264 { (int) '#', "kpnumlock", N_("NumLock on keypad") },
265 { 0, 0 }
266 };
267
268 /* Return the code associated with the symbolic name keyname */
269 int lookup_key (char *keyname)
270 {
271 int i;
272
273 for (i = 0; key_name_conv_tab [i].code; i++){
274 if (strcasecmp (key_name_conv_tab [i].name, keyname))
275 continue;
276 return key_name_conv_tab [i].code;
277 }
278 return 0;
279 }
280