This source file includes following definitions.
- print_item
- print_arrows
- print_buttons
- dialog_menu
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 #include "dialog.h"
23
24 static int menu_width, item_x;
25
26
27
28
29 static void
30 print_item (WINDOW * win, const char *item, int choice, int selected, int hotkey)
31 {
32 int i, j;
33 char menu_item[menu_width+1];
34
35 strncpy(menu_item, item, menu_width);
36 menu_item[menu_width] = 0;
37 j = first_alpha(menu_item);
38
39
40 wattrset (win, menubox_attr);
41 wmove (win, choice, 0);
42 for (i = 0; i < menu_width; i++)
43 waddch (win, ' ');
44 wattrset (win, selected ? item_selected_attr : item_attr);
45 mvwaddstr (win, choice, item_x, menu_item);
46 if (hotkey) {
47 wattrset (win, selected ? tag_key_selected_attr : tag_key_attr);
48 mvwaddch(win, choice, item_x+j, menu_item[j]);
49 }
50 }
51
52
53
54
55 static void
56 print_arrows (WINDOW * win, int choice, int item_no, int scroll,
57 int y, int x, int height)
58 {
59 int cur_y, cur_x;
60
61 getyx(win, cur_y, cur_x);
62
63 wmove(win, y, x);
64
65 if (scroll > 0) {
66 wattrset (win, uarrow_attr);
67 waddch (win, ACS_UARROW);
68 waddstr (win, "(-)");
69 }
70 else {
71 wattrset (win, menubox_attr);
72 waddch (win, ACS_HLINE);
73 waddch (win, ACS_HLINE);
74 waddch (win, ACS_HLINE);
75 waddch (win, ACS_HLINE);
76 }
77
78 y = y + height + 1;
79 wmove(win, y, x);
80
81 if ((height < item_no) && (scroll + choice < item_no - 1)) {
82 wattrset (win, darrow_attr);
83 waddch (win, ACS_DARROW);
84 waddstr (win, "(+)");
85 }
86 else {
87 wattrset (win, menubox_border_attr);
88 waddch (win, ACS_HLINE);
89 waddch (win, ACS_HLINE);
90 waddch (win, ACS_HLINE);
91 waddch (win, ACS_HLINE);
92 }
93
94 wmove(win, cur_y, cur_x);
95 }
96
97
98
99
100 static void
101 print_buttons (WINDOW *win, int height, int width, int selected)
102 {
103 int x = width / 2 - 16;
104 int y = height - 2;
105
106 print_button (win, "Select", y, x, selected == 0);
107 print_button (win, " Exit ", y, x + 12, selected == 1);
108 print_button (win, " Help ", y, x + 24, selected == 2);
109
110 wmove(win, y, x+1+12*selected);
111 wrefresh (win);
112 }
113
114
115
116
117 int
118 dialog_menu (const char *title, const char *prompt, int height, int width,
119 int menu_height, const char *current, int item_no,
120 const char * const * items)
121
122 {
123 int i, j, x, y, box_x, box_y;
124 int key = 0, button = 0, scroll = 0, choice = 0, first_item = 0, max_choice;
125 WINDOW *dialog, *menu;
126
127 max_choice = MIN (menu_height, item_no);
128
129
130 x = (COLS - width) / 2;
131 y = (LINES - height) / 2;
132
133 draw_shadow (stdscr, y, x, height, width);
134
135 dialog = newwin (height, width, y, x);
136 keypad (dialog, TRUE);
137
138 draw_box (dialog, 0, 0, height, width, dialog_attr, border_attr);
139 wattrset (dialog, border_attr);
140 mvwaddch (dialog, height - 3, 0, ACS_LTEE);
141 for (i = 0; i < width - 2; i++)
142 waddch (dialog, ACS_HLINE);
143 wattrset (dialog, dialog_attr);
144 waddch (dialog, ACS_RTEE);
145
146 if (title != NULL) {
147 wattrset (dialog, title_attr);
148 mvwaddch (dialog, 0, (width - strlen(title))/2 - 1, ' ');
149 waddstr (dialog, (char *)title);
150 waddch (dialog, ' ');
151 }
152
153 wattrset (dialog, dialog_attr);
154 print_autowrap (dialog, prompt, width - 2, 1, 3);
155
156 menu_width = width - 6;
157 box_y = height - menu_height - 5;
158 box_x = (width - menu_width) / 2 - 1;
159
160
161 menu = subwin (dialog, menu_height, menu_width,
162 y + box_y + 1, x + box_x + 1);
163 keypad (menu, TRUE);
164
165
166 draw_box (dialog, box_y, box_x, menu_height + 2, menu_width + 2,
167 menubox_border_attr, menubox_attr);
168
169
170
171
172
173 item_x = 0;
174 for (i = 0; i < item_no; i++) {
175 item_x = MAX (item_x, MIN(menu_width, strlen (items[i * 2 + 1]) + 2));
176 if (strcmp(current, items[i*2]) == 0) choice = i;
177 }
178
179 item_x = (menu_width - item_x) / 2;
180
181 if (choice >= max_choice){
182 scroll = first_item = choice - max_choice + 1;
183 choice = max_choice-1;
184 }
185
186
187 for (i=0; i < max_choice; i++) {
188 print_item (menu, items[(first_item + i) * 2 + 1], i, i == choice,
189 (items[(first_item + i)*2][0] != ':'));
190 }
191
192 wnoutrefresh (menu);
193
194 print_arrows(dialog, choice, item_no, scroll,
195 box_y, box_x+item_x+1, menu_height);
196
197 print_buttons (dialog, height, width, 0);
198
199 while (key != ESC) {
200 key = wgetch (dialog);
201
202 for (i = choice+1; i < max_choice; i++) {
203 j = first_alpha(items[(scroll+i)*2+1]);
204 if (toupper(key) == toupper(items[(scroll+i)*2+1][j]))
205 break;
206 }
207 if (i == max_choice)
208 for (i = 0; i < max_choice; i++) {
209 j = first_alpha(items[(scroll+i)*2+1]);
210 if (toupper(key) == toupper(items[(scroll+i)*2+1][j]))
211 break;
212 }
213
214 if (i < max_choice || key == KEY_UP || key == KEY_DOWN || key == '-' || key == '+') {
215 if (key == KEY_UP || key == '-') {
216 if (choice == 0) {
217 if (scroll) {
218
219
220 if (menu_height > 1) {
221
222 print_item (menu, items[scroll*2+1], 0, FALSE,
223 (items[scroll*2][0] != ':'));
224 scrollok (menu, TRUE);
225 wscrl (menu, -1);
226 scrollok (menu, FALSE);
227 }
228 scroll--;
229 print_item (menu, items[scroll * 2 + 1], 0, TRUE,
230 (items[scroll*2][0] != ':'));
231 wnoutrefresh (menu);
232
233 print_arrows(dialog, choice, item_no, scroll,
234 box_y, box_x+item_x+1, menu_height);
235
236 }
237 continue;
238 } else
239 i = choice - 1;
240 } else if (key == KEY_DOWN || key == '+')
241 if (choice == max_choice - 1) {
242 if (scroll + choice < item_no - 1) {
243
244 if (menu_height > 1) {
245
246 print_item (menu, items[(scroll + max_choice - 1)
247 * 2 + 1], max_choice - 1, FALSE,
248 (items[(scroll+max_choice-1)*2][0] != ':'));
249 scrollok (menu, TRUE);
250 scroll (menu);
251 scrollok (menu, FALSE);
252 }
253 scroll++;
254 print_item (menu, items[(scroll+max_choice-1)*2+1],
255 max_choice-1, TRUE,
256 (items[(scroll+max_choice-1)*2][0] != ':'));
257
258 wnoutrefresh (menu);
259
260 print_arrows(dialog, choice, item_no, scroll,
261 box_y, box_x+item_x+1, menu_height);
262
263 wrefresh (dialog);
264 }
265 continue;
266 } else
267 i = choice + 1;
268
269 if (i != choice) {
270
271 print_item (menu, items[(scroll+choice)*2+1], choice, FALSE,
272 (items[(scroll+choice)*2][0] != ':'));
273
274
275 choice = i;
276 print_item (menu, items[(scroll+choice)*2+1], choice, TRUE,
277 (items[(scroll+choice)*2][0] != ':'));
278 wnoutrefresh (menu);
279 wrefresh (dialog);
280 }
281 continue;
282 }
283
284 switch (key) {
285 case KEY_LEFT:
286 case TAB:
287 case KEY_RIGHT:
288 button = ((key == KEY_LEFT ? --button : ++button) < 0)
289 ? 2 : (button > 2 ? 0 : button);
290
291 print_buttons(dialog, height, width, button);
292 wrefresh (dialog);
293 break;
294 case ' ':
295 case 'S':
296 case 's':
297 delwin (dialog);
298 fprintf(stderr, items[(scroll + choice) * 2]);
299 return 0;
300 case 'H':
301 case 'h':
302 case '?':
303 button = 2;
304 case '\n':
305 delwin (dialog);
306 if (button == 2)
307 fprintf(stderr, "%s \"%s\"",
308 items[(scroll + choice) * 2],
309 items[(scroll + choice) * 2 + 1] +
310 first_alpha(items[(scroll + choice) * 2 + 1]));
311 else
312 fprintf(stderr, items[(scroll + choice) * 2]);
313
314 return button;
315 case 'E':
316 case 'e':
317 case 'X':
318 case 'x':
319 key = ESC;
320 case ESC:
321 break;
322 }
323 }
324
325 delwin (dialog);
326 return -1;
327 }