1 /*
2 * fbcmd.cc
3 *
4 * Copyright (C) 1998 Jiann-Ching Liu
5 */
6
7 #include <sys/types.h>
8 #include <sys/stat.h>
9 #include <stdio.h>
10 #include <stdlib.h>
11 #include <string.h>
12 #include <unistd.h>
13 #include "qe_config.h"
14 #include "filebuffer.h"
15 #include "colors.h"
16 #include "messages.h"
17
18 static int saved_flag = 0;
19
cmd_insert_toggle(void)20 int filebuffer::cmd_insert_toggle(void) {
21 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
22 input_mode = insert_mode;
23 input_mode = (input_mode + 1) % 2;
24 insert_mode = input_mode;
25 display_status();
26 return 0;
27 }
28
cmd_insert_mode(void)29 int filebuffer::cmd_insert_mode(void) {
30 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
31 input_mode = insert_mode;
32 input_mode = FB_INSERT_MODE;
33 display_status();
34 return 0;
35 }
36
cmd_toggle_historykey(void)37 int filebuffer::cmd_toggle_historykey(void) {
38 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
39
40 history_key = (history_key + 1) % 4;
41 return 0;
42 }
43
cmd_toggle_searchcase(void)44 int filebuffer::cmd_toggle_searchcase(void) {
45 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
46
47 search_case = (search_case + 1) % 2;
48 return 0;
49 }
50
cmd_toggle_dirsort(void)51 int filebuffer::cmd_toggle_dirsort(void) {
52 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
53
54 dir_sort = (dir_sort + 1) % 3;
55 return 0;
56 }
57
cmd_replace_mode(void)58 int filebuffer::cmd_replace_mode(void) {
59 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
60
61 input_mode = FB_REPLACE_MODE;
62 display_status();
63 return 0;
64 }
65
cmd_toggle_blankcompress(void)66 int filebuffer::cmd_toggle_blankcompress(void) {
67 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
68
69 blank_compress = (blank_compress + 1) % 2;
70 return 0;
71 }
72
73
cmd_command_toggle(void)74 int filebuffer::cmd_command_toggle(void) {
75 return (mode == FB_DATAAREA_MODE) ? cmd_cursor_cmd() : cmd_cursor_data();
76 }
77
cmd_cursor_data(void)78 int filebuffer::cmd_cursor_data(void) {
79 if (mode != FB_DATAAREA_MODE) load_workbuffer();
80 mode = FB_DATAAREA_MODE;
81 return 0;
82 }
83
cmd_cursor_cmd(void)84 int filebuffer::cmd_cursor_cmd(void) {
85 if (mode != FB_COMMAND_MODE) write_workbuffer(QE_IF_NECESSARY);
86 mode = FB_COMMAND_MODE;
87 return 0;
88 }
89
cmd_split(void)90 int filebuffer::cmd_split(void) {
91 if (read_only) {
92 display_messages(MSG_READ_ONLY_FILE);
93 return 0;
94 }
95
96 // if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
97
98 cmd_cursor_data();
99
100 if (buffer_x > workbuflen-1) {
101 buffer_x = workbufidx = workbuflen - 1;
102 linebuffer *nl = new linebuffer("");
103 nl->next = current->next;
104 nl->previous = current;
105 current->next->previous = nl;
106 current->next = nl;
107 total_line++;
108 cmd_endline();
109 } else {
110 // wprintw(win, "[split]");
111 workbuffer[workbuflen] = '\0';
112 linebuffer *nl = new linebuffer(&workbuffer[workbufidx]);
113 nl->next = current->next;
114 nl->previous = current;
115 current->next->previous = nl;
116 current->next = nl;
117 total_line++;
118 workbuffer[workbufidx] = '\0';
119 workbuflen = (buffer_x = workbufidx) + 1;
120 }
121 write_workbuffer(QE_FORCE);
122 fix_all_mark_position(FIX_MARK_INSERT_LINE);
123 refresh_clientarea(0);
124 load_workbuffer();
125 return 0;
126 }
127
cmd_join(void)128 int filebuffer::cmd_join(void) {
129 if (read_only) {
130 display_messages(MSG_READ_ONLY_FILE);
131 return 0;
132 }
133
134 // if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
135
136 if (current->next != tail) {
137 fix_all_mark_position(FIX_MARK_JOIN_LINE);
138
139 linebuffer *ptr= current->next;
140
141 workbuffer[workbuflen] = '\0';
142 strncat(workbuffer, ptr->getString(), MAX_BUFFER_LEN - workbuflen - 2);
143 workbuflen = strlen(workbuffer);
144 current->next = ptr->next;
145 ptr->next->previous = current;
146 total_line--;
147 ptr->~linebuffer();
148 dirty_line = 1;
149 write_workbuffer(QE_FORCE);
150 refresh_clientarea(0);
151 }
152 return 0;
153 }
154
cmd_new(void)155 int filebuffer::cmd_new(void) {
156 return cmd_edit("");
157 }
158
cmd_edit(void)159 int filebuffer::cmd_edit(void) {
160 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
161
162 if (current_buffer == current_buffer->next_buffer) return 0;
163
164
165 write_workbuffer(QE_IF_NECESSARY);
166 current_buffer = current_buffer->next_buffer;
167 if (keep_in_menu == MENU_KEEP_IN_MENU) {
168 keep_in_menu = MENU_NOT_IN_MENU;
169 current_buffer->keep_in_menu = MENU_BACK_TO_MENU;
170 }
171 return RTNVAL_NEXT_BUFFER;
172 }
173
cmd_edit(const char * args,const int ro)174 int filebuffer::cmd_edit(const char *args, const int ro) {
175 if (current_buffer->filename.getLength() == 0 ||
176 strcmp(current_buffer->filename.getString(), args) != 0) {
177 int found = 0;
178
179 write_workbuffer(QE_IF_NECESSARY);
180
181 filebuffer *f = current_buffer;
182 while ((f = f->next_buffer) != current_buffer) {
183 if (f->filename.getLength() != 0 &&
184 strcmp(f->filename.getString(), args) == 0) {
185 found = 1;
186 break;
187 }
188 }
189 if (! found) f = new filebuffer(args);
190 f->read_only = ro;
191 current_buffer = f;
192
193 return RTNVAL_NEXT_BUFFER;
194 }
195 return 0;
196 }
197
cmd_save_all_quit(void)198 int filebuffer::cmd_save_all_quit(void) {
199 quit_confirm = 0;
200
201 if (dirty_flag || dirty_line) cmd_save();
202 cmd_quit();
203
204 return RTNVAL_SAVE_ALL_AND_QUIT;
205 }
206
cmd_quit_all(void)207 int filebuffer::cmd_quit_all(void) {
208 quit_confirm = 0;
209 cmd_quit();
210 return RTNVAL_QUIT_ALL_BUFFER;
211 }
212
cmd_quit(void)213 int filebuffer::cmd_quit(void) {
214
215 write_workbuffer(QE_IF_NECESSARY);
216
217 if (quit_confirm) {
218 if (dirty_flag || dirty_line) {
219 int k;
220
221 display_messages(MSG_REALLY_QUIT);
222
223 while (1) {
224 k = wgetch(win);
225 if (k == 'y' || k == 'Y') break;
226 if (k == 'n' || k == 'N') {
227 display_messages();
228 return 0;
229 }
230 }
231 }
232 }
233
234 return RTNVAL_QUIT_BUFFER;
235 }
236
cmd_file(void)237 int filebuffer::cmd_file(void) {
238 write_workbuffer(QE_IF_NECESSARY);
239 saved_flag = 0;
240 cmd_save();
241 if (saved_flag && dirty_flag == 0) return cmd_quit();
242 return 0;
243 }
244
cmd_save(void)245 int filebuffer::cmd_save(void) {
246 if (filename.getLength() != 0) {
247 FILE *fd;
248 linebuffer *ptr = head;
249 struct stat stbuf;
250 int mode_changed = 0;
251
252 write_workbuffer(QE_IF_NECESSARY);
253
254 if (access(filename.getString(), F_OK) == 0 &&
255 access(filename.getString(), W_OK) != 0) {
256 int k;
257 display_messages(MSG_WRITE_FORCE);
258 while (1) {
259 k = wgetch(win);
260 if (k == 'y' || k == 'Y') break;
261 if (k == 'n' || k == 'N') {
262 display_messages();
263 return 0;
264 }
265 }
266 stat(filename.getString(), &stbuf);
267 chmod(filename.getString(), stbuf.st_mode | 0222);
268 mode_changed = 1;
269 }
270
271 if ((fd = fopen(filename.getString(), "w+")) != NULL) {
272 int i, j, k, m, len;
273 char buffer[MAX_BUFFER_LEN+1];
274
275 while ((ptr = ptr->next) != tail) {
276 if (blank_compress) {
277 len = ptr->getLength();
278 m = 0;
279
280 for (i = TAB_SPACE; i < len; i += TAB_SPACE) {
281 for (j = i - 1; j >= i - TAB_SPACE; j--)
282 if ((*ptr)[j] != ' ')
283 break;
284
285 for (k = i - TAB_SPACE; k <= j; k++)
286 buffer[m++] = (*ptr)[k];
287
288 if (j == i-2) {
289 buffer[m++] = ' ';
290 } else if (j < i-2) {
291 buffer[m++] = '\t';
292 }
293 }
294 for (i = i - TAB_SPACE; i <= len; i++)
295 buffer[m++] = (*ptr)[i];
296
297 for (m--; m >= 0; m--) {
298 if (buffer[m] != ' ' && buffer[m] != '\t'
299 && buffer[m] != '\0')
300 break;
301 buffer[m] = '\0';
302 }
303
304 fprintf(fd, "%s\n", buffer);
305 } else {
306 fprintf(fd, "%s\n", ptr->getString());
307 }
308 }
309 fclose(fd);
310 dirty_flag = 0;
311 display_filename();
312 // setattr(win, ATTRIBUTE_status_line);
313 // mvwprintw(win, screen_y-2, 0, "%-30s ", filename);
314 display_messages(MSG_FILE_SAVED);
315 saved_flag = 1;
316 } else {
317 display_messages(MSG_ERROR_OPEN_FILE);
318 }
319
320 if (mode_changed) chmod(filename.getString(), stbuf.st_mode);
321 } else {
322 display_messages(MSG_MESSING_FILE_NAME);
323 }
324 // mode = FB_COMMAND_MODE;
325
326 return 0;
327 }
328
cmd_undo(void)329 int filebuffer::cmd_undo(void) {
330 load_workbuffer();
331 dirty_line = 0;
332 refresh_bufferline();
333
334 return 0;
335 }
336
cmd_first_nonblank(void)337 int filebuffer::cmd_first_nonblank(void) {
338 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
339
340 cmd_cursor_data();
341
342 for (workbufidx = 0; workbufidx < workbuflen; workbufidx++)
343 if (workbuffer[workbufidx] != ' ')
344 break;
345
346 buffer_x = workbufidx;
347
348 moveto(buffer_y, buffer_x);
349
350 // if (workbufidx < screen_x - 1) {
351 // cursor_x = workbufidx;
352 // if (left_col_no != 0) {
353 // left_col_no = 0;
354 // refresh_clientarea();
355 // refresh_bufferline();
356 // }
357 // } else {
358 // if ((unsigned int) workbufidx >= left_col_no &&
359 // (unsigned int) workbufidx < left_col_no + screen_x -1) {
360 // cursor_x = workbufidx - left_col_no;
361 // } else {
362 // cursor_x = screen_x - 1;
363 // left_col_no = workbufidx - cursor_x;
364 // refresh_clientarea();
365 // refresh_bufferline();
366 // }
367 // }
368 return 0;
369 }
370
cmd_insertline(void)371 int filebuffer::cmd_insertline(void) {
372 if (read_only) {
373 display_messages(MSG_READ_ONLY_FILE);
374 return 0;
375 }
376
377 if (keep_in_menu == MENU_IN_MENU) keep_in_menu = MENU_KEEP_IN_MENU;
378
379 write_workbuffer(QE_FORCE);
380
381 linebuffer *newline = new linebuffer("");
382 newline->next = current->next;
383 newline->previous = current;
384 newline->next->previous = newline;
385 current->next = newline;
386 current = newline;
387
388 buffer_x = 0;
389 buffer_y++;
390
391 cursor_x = 0;
392
393 if (cursor_y == screen_y-4) {
394 top_line_no++;
395 topline = topline->next;
396 } else {
397 cursor_y++;
398 }
399
400 total_line++;
401 fix_all_mark_position(FIX_MARK_INSERT_LINE);
402 refresh_clientarea(0);
403 load_workbuffer();
404
405 return 0;
406 }
407
cmd_beep(void)408 int filebuffer::cmd_beep(void) {
409 beep();
410 return 0;
411 }
412
cmd_cmdquote(const char * quote)413 int filebuffer::cmd_cmdquote(const char *quote) {
414 cmd_execute(quote);
415 return 0;
416 }
417