This source file includes following definitions.
- edit_load_status_update_cb
- edit_load_file_fast
- edit_find_filter
- edit_get_filter
- edit_insert_stream
- check_file_access
- edit_load_file
- edit_load_position
- edit_save_position
- edit_purge_widget
- edit_pop_undo_action
- edit_pop_redo_action
- get_prev_undo_action
- edit_modification
- is_in_indent
- is_blank
- edit_find_line
- edit_move_up_paragraph
- edit_move_down_paragraph
- edit_begin_page
- edit_end_page
- edit_move_to_top
- edit_move_to_bottom
- edit_cursor_to_bol
- edit_cursor_to_eol
- my_type_of
- edit_left_word_move
- edit_left_word_move_cmd
- edit_right_word_move
- edit_right_word_move_cmd
- edit_right_char_move_cmd
- edit_left_char_move_cmd
- edit_move_updown
- edit_right_delete_word
- edit_left_delete_word
- edit_do_undo
- edit_do_redo
- edit_group_undo
- edit_delete_to_line_end
- edit_delete_to_line_begin
- is_aligned_on_a_tab
- right_of_four_spaces
- left_of_four_spaces
- edit_auto_indent
- edit_double_newline
- insert_spaces_tab
- edit_tab_cmd
- check_and_wrap_line
- edit_get_bracket
- edit_goto_matching_bracket
- edit_move_block_to_right
- edit_move_block_to_left
- edit_print_string
- edit_insert_column_from_file
- edit_user_menu
- edit_get_write_filter
- edit_write_stream
- is_break_char
- edit_insert_file
- edit_init
- edit_clean
- edit_reload_line
- edit_set_codeset
- edit_push_undo_action
- edit_push_redo_action
- edit_insert
- edit_insert_ahead
- edit_insert_over
- edit_delete
- edit_backspace
- edit_cursor_move
- edit_move_forward3
- edit_get_cursor_offset
- edit_get_col
- edit_update_curs_row
- edit_update_curs_col
- edit_get_curs_col
- edit_scroll_upward
- edit_scroll_downward
- edit_scroll_right
- edit_scroll_left
- edit_move_to_prev_col
- edit_line_is_blank
- edit_move_to_line
- edit_move_display
- edit_push_markers
- edit_set_markers
- eval_marks
- edit_mark_cmd
- edit_mark_current_word_cmd
- edit_mark_current_line_cmd
- edit_delete_line
- edit_push_key_press
- edit_find_bracket
- edit_execute_key_command
- edit_execute_cmd
- edit_stack_init
- edit_stack_free
- edit_move_up
- edit_move_down
- edit_arg_vpath_new
- edit_arg_new
- edit_arg_init
- edit_arg_assign
- edit_arg_free
- edit_get_file_name
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34 #include <config.h>
35 #include <stdio.h>
36 #include <stdarg.h>
37 #include <sys/types.h>
38 #include <unistd.h>
39 #include <string.h>
40 #include <ctype.h>
41 #include <sys/stat.h>
42 #include <stdint.h>
43 #include <stdlib.h>
44
45 #include "lib/global.h"
46
47 #include "lib/tty/color.h"
48 #include "lib/tty/tty.h"
49 #include "lib/tty/key.h"
50 #include "lib/skin.h"
51 #include "lib/fileloc.h"
52 #include "lib/vfs/vfs.h"
53 #include "lib/strutil.h"
54 #include "lib/util.h"
55 #include "lib/timefmt.h"
56 #include "lib/lock.h"
57 #include "lib/widget.h"
58
59 #ifdef HAVE_CHARSET
60 #include "lib/charsets.h"
61 #endif
62
63 #include "src/usermenu.h"
64
65 #include "src/keymap.h"
66
67 #include "edit-impl.h"
68 #include "editwidget.h"
69 #include "editsearch.h"
70 #include "editcomplete.h"
71 #include "editmacros.h"
72 #include "etags.h"
73 #ifdef HAVE_ASPELL
74 #include "spell.h"
75 #endif
76
77
78
79 edit_options_t edit_options = {
80 .word_wrap_line_length = DEFAULT_WRAP_LINE_LENGTH,
81 .typewriter_wrap = FALSE,
82 .auto_para_formatting = FALSE,
83 .fill_tabs_with_spaces = FALSE,
84 .return_does_auto_indent = TRUE,
85 .backspace_through_tabs = FALSE,
86 .fake_half_tabs = TRUE,
87 .persistent_selections = TRUE,
88 .drop_selection_on_copy = TRUE,
89 .cursor_beyond_eol = FALSE,
90 .cursor_after_inserted_block = FALSE,
91 .state_full_filename = FALSE,
92 .line_state = FALSE,
93 .line_state_width = 0,
94 .save_mode = EDIT_QUICK_SAVE,
95 .confirm_save = TRUE,
96 .save_position = TRUE,
97 .syntax_highlighting = TRUE,
98 .group_undo = FALSE,
99 .backup_ext = NULL,
100 .filesize_threshold = NULL,
101 .stop_format_chars = NULL,
102 .visible_tabs = TRUE,
103 .visible_tws = TRUE,
104 .show_right_margin = FALSE,
105 .simple_statusbar = FALSE,
106 .check_nl_at_eof = FALSE
107 };
108
109 int max_undo = 32768;
110
111 gboolean enable_show_tabs_tws = TRUE;
112
113 unsigned int edit_stack_iterator = 0;
114 edit_arg_t edit_history_moveto[MAX_HISTORY_MOVETO];
115
116 const char VERTICAL_MAGIC[] = { '\1', '\1', '\1', '\1', '\n' };
117
118
119
120 #define TEMP_BUF_LEN 1024
121
122 #define space_width 1
123
124
125
126
127
128
129
130
131
132
133
134 static const struct edit_filters
135 {
136 const char *read, *write, *extension;
137 } all_filters[] = {
138
139 { "xz -cd %s 2>&1", "xz > %s", ".xz"},
140 { "zstd -cd %s 2>&1", "zstd > %s", ".zst"},
141 { "lz4 -cd %s 2>&1", "lz4 > %s", ".lz4" },
142 { "lzip -cd %s 2>&1", "lzip > %s", ".lz"},
143 { "lzma -cd %s 2>&1", "lzma > %s", ".lzma" },
144 { "lzop -cd %s 2>&1", "lzop > %s", ".lzo"},
145 { "bzip2 -cd %s 2>&1", "bzip2 > %s", ".bz2" },
146 { "gzip -cd %s 2>&1", "gzip > %s", ".gz" },
147 { "gzip -cd %s 2>&1", "gzip > %s", ".Z" }
148
149 };
150
151 static const off_t filesize_default_threshold = 64 * 1024 * 1024;
152
153
154
155
156
157 static int
158 edit_load_status_update_cb (status_msg_t *sm)
159 {
160 simple_status_msg_t *ssm = SIMPLE_STATUS_MSG (sm);
161 edit_buffer_read_file_status_msg_t *rsm = (edit_buffer_read_file_status_msg_t *) sm;
162 Widget *wd = WIDGET (sm->dlg);
163
164 if (verbose)
165 label_set_textv (ssm->label, _("Loading: %3d%%"),
166 edit_buffer_calc_percent (rsm->buf, rsm->loaded));
167 else
168 label_set_text (ssm->label, _("Loading..."));
169
170 if (rsm->first)
171 {
172 Widget *lw = WIDGET (ssm->label);
173 WRect r;
174
175 r = wd->rect;
176 r.cols = MAX (r.cols, lw->rect.cols + 6);
177 widget_set_size_rect (wd, &r);
178 r = lw->rect;
179 r.x = wd->rect.x + (wd->rect.cols - r.cols) / 2;
180 widget_set_size_rect (lw, &r);
181 rsm->first = FALSE;
182 }
183
184 return status_msg_common_update (sm);
185 }
186
187
188
189
190
191
192
193
194 static gboolean
195 edit_load_file_fast (edit_buffer_t *buf, const vfs_path_t *filename_vpath)
196 {
197 int file;
198 gboolean ret;
199 edit_buffer_read_file_status_msg_t rsm;
200 gboolean aborted;
201
202 file = mc_open (filename_vpath, O_RDONLY | O_BINARY);
203 if (file < 0)
204 {
205 gchar *errmsg;
206
207 errmsg =
208 g_strdup_printf (_("Cannot open %s for reading"), vfs_path_as_str (filename_vpath));
209 edit_error_dialog (_("Error"), errmsg);
210 g_free (errmsg);
211 return FALSE;
212 }
213
214 rsm.first = TRUE;
215 rsm.buf = buf;
216 rsm.loaded = 0;
217
218 status_msg_init (STATUS_MSG (&rsm), _("Load file"), 1.0, simple_status_msg_init_cb,
219 edit_load_status_update_cb, NULL);
220
221 ret = (edit_buffer_read_file (buf, file, buf->size, &rsm, &aborted) == buf->size);
222
223 status_msg_deinit (STATUS_MSG (&rsm));
224
225 if (!ret && !aborted)
226 {
227 gchar *errmsg;
228
229 errmsg = g_strdup_printf (_("Error reading %s"), vfs_path_as_str (filename_vpath));
230 edit_error_dialog (_("Error"), errmsg);
231 g_free (errmsg);
232 }
233
234 mc_close (file);
235 return ret;
236 }
237
238
239
240
241 static int
242 edit_find_filter (const vfs_path_t *filename_vpath)
243 {
244 if (filename_vpath != NULL)
245 {
246 const char *s;
247 size_t i;
248
249 s = vfs_path_as_str (filename_vpath);
250
251 for (i = 0; i < G_N_ELEMENTS (all_filters); i++)
252 if (g_str_has_suffix (s, all_filters[i].extension))
253 return i;
254 }
255
256 return -1;
257 }
258
259
260
261 static char *
262 edit_get_filter (const vfs_path_t *filename_vpath)
263 {
264 int i;
265 char *quoted_name;
266 char *p = NULL;
267
268 i = edit_find_filter (filename_vpath);
269 if (i < 0)
270 return NULL;
271
272 quoted_name = name_quote (vfs_path_as_str (filename_vpath), FALSE);
273 if (quoted_name != NULL)
274 {
275 p = g_strdup_printf (all_filters[i].read, quoted_name);
276 g_free (quoted_name);
277 }
278
279 return p;
280 }
281
282
283
284 static off_t
285 edit_insert_stream (WEdit *edit, FILE *f)
286 {
287 int c;
288 off_t i;
289
290 for (i = 0; (c = fgetc (f)) >= 0; i++)
291 edit_insert (edit, c);
292
293 return i;
294 }
295
296
297
298
299
300
301
302
303
304
305
306 static gboolean
307 check_file_access (WEdit *edit, const vfs_path_t *filename_vpath, struct stat *st)
308 {
309 static uintmax_t threshold = UINTMAX_MAX;
310 int file;
311 gchar *errmsg = NULL;
312 gboolean ret = TRUE;
313
314
315 file = mc_open (filename_vpath, O_NONBLOCK | O_RDONLY | O_BINARY, 0666);
316 if (file < 0)
317 {
318
319
320
321
322 file = mc_open (filename_vpath, O_NONBLOCK | O_RDONLY | O_BINARY | O_CREAT | O_EXCL, 0666);
323 if (file < 0)
324 {
325 errmsg =
326 g_strdup_printf (_("Cannot open %s for reading"), vfs_path_as_str (filename_vpath));
327 goto cleanup;
328 }
329
330
331 edit->delete_file = 1;
332 }
333
334
335 if (mc_fstat (file, st) < 0)
336 {
337 errmsg =
338 g_strdup_printf (_("Cannot get size/permissions for %s"),
339 vfs_path_as_str (filename_vpath));
340 goto cleanup;
341 }
342
343
344 if (!S_ISREG (st->st_mode))
345 {
346 errmsg =
347 g_strdup_printf (_("\"%s\" is not a regular file"), vfs_path_as_str (filename_vpath));
348 goto cleanup;
349 }
350
351
352 if (threshold == UINTMAX_MAX)
353 {
354 gboolean err = FALSE;
355
356 threshold = parse_integer (edit_options.filesize_threshold, &err);
357 if (err)
358 threshold = filesize_default_threshold;
359 }
360
361
362
363
364
365 if (st->st_size > 0)
366 edit->delete_file = 0;
367
368 if ((uintmax_t) st->st_size > threshold)
369 {
370 int act;
371
372 errmsg = g_strdup_printf (_("File \"%s\" is too large.\nOpen it anyway?"),
373 vfs_path_as_str (filename_vpath));
374 act = edit_query_dialog2 (_("Warning"), errmsg, _("&Yes"), _("&No"));
375 MC_PTR_FREE (errmsg);
376
377 if (act != 0)
378 ret = FALSE;
379 }
380
381 cleanup:
382 (void) mc_close (file);
383
384 if (errmsg != NULL)
385 {
386 edit_error_dialog (_("Error"), errmsg);
387 g_free (errmsg);
388 ret = FALSE;
389 }
390
391 return ret;
392 }
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408 static gboolean
409 edit_load_file (WEdit *edit)
410 {
411 gboolean fast_load = TRUE;
412
413
414 if (edit_find_filter (edit->filename_vpath) >= 0)
415 fast_load = FALSE;
416
417
418
419
420
421 if (edit->filename_vpath != NULL)
422 {
423
424
425
426
427 if (!vfs_file_is_local (edit->filename_vpath))
428 fast_load = FALSE;
429
430
431 if (!check_file_access (edit, edit->filename_vpath, &edit->stat1))
432 {
433 edit_clean (edit);
434 return FALSE;
435 }
436 }
437 else
438 {
439
440 fast_load = FALSE;
441 }
442
443 if (fast_load)
444 {
445 edit_buffer_init (&edit->buffer, edit->stat1.st_size);
446
447 if (!edit_load_file_fast (&edit->buffer, edit->filename_vpath))
448 {
449 edit_clean (edit);
450 return FALSE;
451 }
452 }
453 else
454 {
455 edit_buffer_init (&edit->buffer, 0);
456
457 if (edit->filename_vpath != NULL
458 && *(vfs_path_get_by_index (edit->filename_vpath, 0)->path) != '\0')
459 {
460 edit->undo_stack_disable = 1;
461 if (edit_insert_file (edit, edit->filename_vpath) < 0)
462 {
463 edit_clean (edit);
464 return FALSE;
465 }
466 edit->undo_stack_disable = 0;
467 }
468 }
469 edit->lb = LB_ASIS;
470 return TRUE;
471 }
472
473
474
475
476
477
478
479
480
481
482 static void
483 edit_load_position (WEdit *edit, gboolean load_position)
484 {
485 long line, column;
486 off_t offset;
487 off_t b;
488
489 if (edit->filename_vpath == NULL
490 || *(vfs_path_get_by_index (edit->filename_vpath, 0)->path) == '\0')
491 return;
492
493 load_file_position (edit->filename_vpath, &line, &column, &offset, &edit->serialized_bookmarks);
494
495 book_mark_restore (edit, BOOK_MARK_COLOR);
496
497 if (!load_position)
498 return;
499
500 if (line > 0)
501 {
502 edit_move_to_line (edit, line - 1);
503 edit->prev_col = column;
504 }
505 else if (offset > 0)
506 {
507 edit_cursor_move (edit, offset);
508 line = edit->buffer.curs_line;
509 edit->search_start = edit->buffer.curs1;
510 }
511
512 b = edit_buffer_get_current_bol (&edit->buffer);
513 edit_move_to_prev_col (edit, b);
514 edit_move_display (edit, line - (WIDGET (edit)->rect.lines / 2));
515 }
516
517
518
519
520 static void
521 edit_save_position (WEdit *edit)
522 {
523 if (edit->filename_vpath == NULL
524 || *(vfs_path_get_by_index (edit->filename_vpath, 0)->path) == '\0')
525 return;
526
527 book_mark_serialize (edit, BOOK_MARK_COLOR);
528 save_file_position (edit->filename_vpath, edit->buffer.curs_line + 1, edit->curs_col,
529 edit->buffer.curs1, edit->serialized_bookmarks);
530 edit->serialized_bookmarks = NULL;
531 }
532
533
534
535
536 static void
537 edit_purge_widget (WEdit *edit)
538 {
539 size_t len = sizeof (WEdit) - sizeof (Widget);
540 char *start = (char *) edit + sizeof (Widget);
541 memset (start, 0, len);
542 }
543
544
545
546
547
548
549
550
551 static long
552 edit_pop_undo_action (WEdit *edit)
553 {
554 long c;
555 unsigned long sp = edit->undo_stack_pointer;
556
557 if (sp == edit->undo_stack_bottom)
558 return STACK_BOTTOM;
559
560 sp = (sp - 1) & edit->undo_stack_size_mask;
561 c = edit->undo_stack[sp];
562 if (c >= 0)
563 {
564
565 edit->undo_stack_pointer = (edit->undo_stack_pointer - 1) & edit->undo_stack_size_mask;
566 return c;
567 }
568
569 if (sp == edit->undo_stack_bottom)
570 return STACK_BOTTOM;
571
572 c = edit->undo_stack[(sp - 1) & edit->undo_stack_size_mask];
573 if (edit->undo_stack[sp] == -2)
574 {
575
576 edit->undo_stack_pointer = sp;
577 }
578 else
579 edit->undo_stack[sp]++;
580
581 return c;
582 }
583
584
585
586 static long
587 edit_pop_redo_action (WEdit *edit)
588 {
589 long c;
590 unsigned long sp = edit->redo_stack_pointer;
591
592 if (sp == edit->redo_stack_bottom)
593 return STACK_BOTTOM;
594
595 sp = (sp - 1) & edit->redo_stack_size_mask;
596 c = edit->redo_stack[sp];
597 if (c >= 0)
598 {
599 edit->redo_stack_pointer = (edit->redo_stack_pointer - 1) & edit->redo_stack_size_mask;
600 return c;
601 }
602
603 if (sp == edit->redo_stack_bottom)
604 return STACK_BOTTOM;
605
606 c = edit->redo_stack[(sp - 1) & edit->redo_stack_size_mask];
607 if (edit->redo_stack[sp] == -2)
608 edit->redo_stack_pointer = sp;
609 else
610 edit->redo_stack[sp]++;
611
612 return c;
613 }
614
615
616
617 static long
618 get_prev_undo_action (WEdit *edit)
619 {
620 long c;
621 unsigned long sp = edit->undo_stack_pointer;
622
623 if (sp == edit->undo_stack_bottom)
624 return STACK_BOTTOM;
625
626 sp = (sp - 1) & edit->undo_stack_size_mask;
627 c = edit->undo_stack[sp];
628 if (c >= 0)
629 return c;
630
631 if (sp == edit->undo_stack_bottom)
632 return STACK_BOTTOM;
633
634 c = edit->undo_stack[(sp - 1) & edit->undo_stack_size_mask];
635 return c;
636 }
637
638
639
640
641 static void
642 edit_modification (WEdit *edit)
643 {
644 edit->caches_valid = FALSE;
645
646
647 if (edit->modified == 0 && edit->delete_file == 0)
648 edit->locked = lock_file (edit->filename_vpath);
649 edit->modified = 1;
650 }
651
652
653
654
655
656
657
658
659
660
661
662 static gboolean
663 is_in_indent (const edit_buffer_t *buf)
664 {
665 off_t p;
666
667 for (p = edit_buffer_get_current_bol (buf); p < buf->curs1; p++)
668 if (strchr (" \t", edit_buffer_get_byte (buf, p)) == NULL)
669 return FALSE;
670
671 return TRUE;
672 }
673
674
675
676
677
678
679
680
681
682
683 static gboolean
684 is_blank (const edit_buffer_t *buf, off_t offset)
685 {
686 off_t s, f;
687
688 s = edit_buffer_get_bol (buf, offset);
689 f = edit_buffer_get_eol (buf, offset);
690 for (; s < f; s++)
691 {
692 int c;
693
694 c = edit_buffer_get_byte (buf, s);
695 if (!isspace (c))
696 return FALSE;
697 }
698 return TRUE;
699 }
700
701
702
703
704 static off_t
705 edit_find_line (WEdit *edit, long line)
706 {
707 long i;
708 long j = 0;
709 long m = 2000000000;
710
711 if (!edit->caches_valid)
712 {
713 memset (edit->line_numbers, 0, sizeof (edit->line_numbers));
714 memset (edit->line_offsets, 0, sizeof (edit->line_offsets));
715
716 edit->line_numbers[1] = edit->buffer.curs_line;
717 edit->line_offsets[1] = edit_buffer_get_current_bol (&edit->buffer);
718 edit->line_numbers[2] = edit->buffer.lines;
719 edit->line_offsets[2] = edit_buffer_get_bol (&edit->buffer, edit->buffer.size);
720 edit->caches_valid = TRUE;
721 }
722 if (line >= edit->buffer.lines)
723 return edit->line_offsets[2];
724 if (line <= 0)
725 return 0;
726
727 for (i = 0; i < N_LINE_CACHES; i++)
728 {
729 long n;
730
731 n = labs (edit->line_numbers[i] - line);
732 if (n < m)
733 {
734 m = n;
735 j = i;
736 }
737 }
738 if (m == 0)
739 return edit->line_offsets[j];
740 if (m == 1 && j >= 3)
741 i = j;
742 else
743 i = 3 + (rand () % (N_LINE_CACHES - 3));
744 if (line > edit->line_numbers[j])
745 edit->line_offsets[i] =
746 edit_buffer_get_forward_offset (&edit->buffer, edit->line_offsets[j],
747 line - edit->line_numbers[j], 0);
748 else
749 edit->line_offsets[i] =
750 edit_buffer_get_backward_offset (&edit->buffer, edit->line_offsets[j],
751 edit->line_numbers[j] - line);
752 edit->line_numbers[i] = line;
753 return edit->line_offsets[i];
754 }
755
756
757
758
759
760 static void
761 edit_move_up_paragraph (WEdit *edit, gboolean do_scroll)
762 {
763 long i = 0;
764
765 if (edit->buffer.curs_line > 1)
766 {
767 if (!edit_line_is_blank (edit, edit->buffer.curs_line))
768 {
769 for (i = edit->buffer.curs_line - 1; i != 0; i--)
770 if (edit_line_is_blank (edit, i))
771 break;
772 }
773 else if (edit_line_is_blank (edit, edit->buffer.curs_line - 1))
774 {
775 for (i = edit->buffer.curs_line - 1; i != 0; i--)
776 if (!edit_line_is_blank (edit, i))
777 {
778 i++;
779 break;
780 }
781 }
782 else
783 {
784 for (i = edit->buffer.curs_line - 1; i != 0; i--)
785 if (edit_line_is_blank (edit, i))
786 break;
787 }
788 }
789
790 edit_move_up (edit, edit->buffer.curs_line - i, do_scroll);
791 }
792
793
794
795
796
797 static void
798 edit_move_down_paragraph (WEdit *edit, gboolean do_scroll)
799 {
800 long i;
801
802 if (edit->buffer.curs_line >= edit->buffer.lines - 1)
803 i = edit->buffer.lines;
804 else if (!edit_line_is_blank (edit, edit->buffer.curs_line))
805 {
806 for (i = edit->buffer.curs_line + 1; i != 0; i++)
807 if (edit_line_is_blank (edit, i) || i >= edit->buffer.lines)
808 break;
809 }
810 else if (edit_line_is_blank (edit, edit->buffer.curs_line + 1))
811 {
812 for (i = edit->buffer.curs_line + 1; i != 0; i++)
813 if (!edit_line_is_blank (edit, i) || i > edit->buffer.lines)
814 {
815 i--;
816 break;
817 }
818 }
819 else
820 {
821 for (i = edit->buffer.curs_line + 1; i != 0; i++)
822 if (edit_line_is_blank (edit, i) || i >= edit->buffer.lines)
823 break;
824 }
825 edit_move_down (edit, i - edit->buffer.curs_line, do_scroll);
826 }
827
828
829
830 static void
831 edit_begin_page (WEdit *edit)
832 {
833 edit_update_curs_row (edit);
834 edit_move_up (edit, edit->curs_row, FALSE);
835 }
836
837
838
839 static void
840 edit_end_page (WEdit *edit)
841 {
842 edit_update_curs_row (edit);
843 edit_move_down (edit, WIDGET (edit)->rect.lines - edit->curs_row - 1, FALSE);
844 }
845
846
847
848
849
850 static void
851 edit_move_to_top (WEdit *edit)
852 {
853 if (edit->buffer.curs_line != 0)
854 {
855 edit_cursor_move (edit, -edit->buffer.curs1);
856 edit_move_to_prev_col (edit, 0);
857 edit->force |= REDRAW_PAGE;
858 edit->search_start = 0;
859 edit_update_curs_row (edit);
860 }
861 }
862
863
864
865
866 static void
867 edit_move_to_bottom (WEdit *edit)
868 {
869 if (edit->buffer.curs_line < edit->buffer.lines)
870 {
871 edit_move_down (edit, edit->buffer.lines - edit->curs_row, FALSE);
872 edit->start_display = edit->buffer.size;
873 edit->start_line = edit->buffer.lines;
874 edit_scroll_upward (edit, WIDGET (edit)->rect.lines - 1);
875 edit->force |= REDRAW_PAGE;
876 }
877 }
878
879
880
881
882 static void
883 edit_cursor_to_bol (WEdit *edit)
884 {
885 off_t b;
886
887 b = edit_buffer_get_current_bol (&edit->buffer);
888 edit_cursor_move (edit, b - edit->buffer.curs1);
889 edit->search_start = edit->buffer.curs1;
890 edit->prev_col = edit_get_col (edit);
891 edit->over_col = 0;
892 }
893
894
895
896
897 static void
898 edit_cursor_to_eol (WEdit *edit)
899 {
900 off_t b;
901
902 b = edit_buffer_get_current_eol (&edit->buffer);
903 edit_cursor_move (edit, b - edit->buffer.curs1);
904 edit->search_start = edit->buffer.curs1;
905 edit->prev_col = edit_get_col (edit);
906 edit->over_col = 0;
907 }
908
909
910
911 static unsigned long
912 my_type_of (int c)
913 {
914 unsigned long r = 0;
915 const char *q;
916 const char chars_move_whole_word[] =
917 "!=&|<>^~ !:;, !'!`!.?!\"!( !) !{ !} !Aa0 !+-*/= |<> ![ !] !\\#! ";
918
919 if (c == 0)
920 return 0;
921 if (c == '!')
922 return 2;
923
924 if (g_ascii_isupper ((gchar) c))
925 c = 'A';
926 else if (g_ascii_islower ((gchar) c))
927 c = 'a';
928 else if (g_ascii_isalpha (c))
929 c = 'a';
930 else if (isdigit (c))
931 c = '0';
932 else if (isspace (c))
933 c = ' ';
934 q = strchr (chars_move_whole_word, c);
935 if (q == NULL)
936 return 0xFFFFFFFFUL;
937
938 do
939 {
940 unsigned long x;
941 const char *p;
942
943 for (x = 1, p = chars_move_whole_word; p < q; p++)
944 if (*p == '!')
945 x <<= 1;
946 r |= x;
947 }
948 while ((q = strchr (q + 1, c)) != NULL);
949
950 return r;
951 }
952
953
954
955 static void
956 edit_left_word_move (WEdit *edit, int s)
957 {
958 while (TRUE)
959 {
960 int c1, c2;
961
962 if (edit->column_highlight
963 && edit->mark1 != edit->mark2
964 && edit->over_col == 0
965 && edit->buffer.curs1 == edit_buffer_get_current_bol (&edit->buffer))
966 break;
967 edit_cursor_move (edit, -1);
968 if (edit->buffer.curs1 == 0)
969 break;
970 c1 = edit_buffer_get_previous_byte (&edit->buffer);
971 if (c1 == '\n')
972 break;
973 c2 = edit_buffer_get_current_byte (&edit->buffer);
974 if (c2 == '\n')
975 break;
976 if ((my_type_of (c1) & my_type_of (c2)) == 0)
977 break;
978 if (isspace (c1) && !isspace (c2))
979 break;
980 if (s != 0 && !isspace (c1) && isspace (c2))
981 break;
982 }
983 }
984
985
986
987 static void
988 edit_left_word_move_cmd (WEdit *edit)
989 {
990 edit_left_word_move (edit, 0);
991 edit->force |= REDRAW_PAGE;
992 }
993
994
995
996 static void
997 edit_right_word_move (WEdit *edit, int s)
998 {
999 while (TRUE)
1000 {
1001 int c1, c2;
1002
1003 if (edit->column_highlight
1004 && edit->mark1 != edit->mark2
1005 && edit->over_col == 0
1006 && edit->buffer.curs1 == edit_buffer_get_current_eol (&edit->buffer))
1007 break;
1008 edit_cursor_move (edit, 1);
1009 if (edit->buffer.curs1 >= edit->buffer.size)
1010 break;
1011 c1 = edit_buffer_get_previous_byte (&edit->buffer);
1012 if (c1 == '\n')
1013 break;
1014 c2 = edit_buffer_get_current_byte (&edit->buffer);
1015 if (c2 == '\n')
1016 break;
1017 if ((my_type_of (c1) & my_type_of (c2)) == 0)
1018 break;
1019 if (isspace (c1) && !isspace (c2))
1020 break;
1021 if (s != 0 && !isspace (c1) && isspace (c2))
1022 break;
1023 }
1024 }
1025
1026
1027
1028 static void
1029 edit_right_word_move_cmd (WEdit *edit)
1030 {
1031 edit_right_word_move (edit, 0);
1032 edit->force |= REDRAW_PAGE;
1033 }
1034
1035
1036
1037 static void
1038 edit_right_char_move_cmd (WEdit *edit)
1039 {
1040 int char_length = 1;
1041 int c;
1042
1043 #ifdef HAVE_CHARSET
1044 if (edit->utf8)
1045 {
1046 c = edit_buffer_get_utf (&edit->buffer, edit->buffer.curs1, &char_length);
1047 if (char_length < 1)
1048 char_length = 1;
1049 }
1050 else
1051 #endif
1052 c = edit_buffer_get_current_byte (&edit->buffer);
1053
1054 if (edit_options.cursor_beyond_eol && c == '\n')
1055 edit->over_col++;
1056 else
1057 edit_cursor_move (edit, char_length);
1058 }
1059
1060
1061
1062 static void
1063 edit_left_char_move_cmd (WEdit *edit)
1064 {
1065 int char_length = 1;
1066
1067 if (edit->column_highlight
1068 && edit_options.cursor_beyond_eol
1069 && edit->mark1 != edit->mark2
1070 && edit->over_col == 0 && edit->buffer.curs1 == edit_buffer_get_current_bol (&edit->buffer))
1071 return;
1072 #ifdef HAVE_CHARSET
1073 if (edit->utf8)
1074 {
1075 edit_buffer_get_prev_utf (&edit->buffer, edit->buffer.curs1, &char_length);
1076 if (char_length < 1)
1077 char_length = 1;
1078 }
1079 #endif
1080
1081 if (edit_options.cursor_beyond_eol && edit->over_col > 0)
1082 edit->over_col--;
1083 else
1084 edit_cursor_move (edit, -char_length);
1085 }
1086
1087
1088
1089
1090
1091
1092
1093 static void
1094 edit_move_updown (WEdit *edit, long lines, gboolean do_scroll, gboolean direction)
1095 {
1096 long p;
1097 long l = direction ? edit->buffer.curs_line : edit->buffer.lines - edit->buffer.curs_line;
1098
1099 if (lines > l)
1100 lines = l;
1101
1102 if (lines == 0)
1103 return;
1104
1105 if (lines > 1)
1106 edit->force |= REDRAW_PAGE;
1107 if (do_scroll)
1108 {
1109 if (direction)
1110 edit_scroll_upward (edit, lines);
1111 else
1112 edit_scroll_downward (edit, lines);
1113 }
1114 p = edit_buffer_get_current_bol (&edit->buffer);
1115 p = direction ? edit_buffer_get_backward_offset (&edit->buffer, p, lines) :
1116 edit_buffer_get_forward_offset (&edit->buffer, p, lines, 0);
1117 edit_cursor_move (edit, p - edit->buffer.curs1);
1118 edit_move_to_prev_col (edit, p);
1119
1120 #ifdef HAVE_CHARSET
1121
1122 if (edit->buffer.curs1 > 0 && edit->buffer.curs1 + 1 < edit->buffer.size
1123 && edit_buffer_get_current_byte (&edit->buffer) >= 256)
1124 {
1125 edit_right_char_move_cmd (edit);
1126 edit_left_char_move_cmd (edit);
1127 }
1128 #endif
1129
1130 edit->search_start = edit->buffer.curs1;
1131 edit->found_len = 0;
1132 }
1133
1134
1135
1136 static void
1137 edit_right_delete_word (WEdit *edit)
1138 {
1139 while (edit->buffer.curs1 < edit->buffer.size)
1140 {
1141 int c1, c2;
1142
1143 c1 = edit_delete (edit, TRUE);
1144 if (c1 == '\n')
1145 break;
1146 c2 = edit_buffer_get_current_byte (&edit->buffer);
1147 if (c2 == '\n')
1148 break;
1149 if ((isspace (c1) == 0) != (isspace (c2) == 0))
1150 break;
1151 if ((my_type_of (c1) & my_type_of (c2)) == 0)
1152 break;
1153 }
1154 }
1155
1156
1157
1158 static void
1159 edit_left_delete_word (WEdit *edit)
1160 {
1161 while (edit->buffer.curs1 > 0)
1162 {
1163 int c1, c2;
1164
1165 c1 = edit_backspace (edit, TRUE);
1166 if (c1 == '\n')
1167 break;
1168 c2 = edit_buffer_get_previous_byte (&edit->buffer);
1169 if (c2 == '\n')
1170 break;
1171 if ((isspace (c1) == 0) != (isspace (c2) == 0))
1172 break;
1173 if ((my_type_of (c1) & my_type_of (c2)) == 0)
1174 break;
1175 }
1176 }
1177
1178
1179
1180
1181
1182
1183
1184 static void
1185 edit_do_undo (WEdit *edit)
1186 {
1187 long ac;
1188 long count = 0;
1189
1190 edit->undo_stack_disable = 1;
1191 edit->over_col = 0;
1192
1193 while ((ac = edit_pop_undo_action (edit)) < KEY_PRESS)
1194 {
1195 off_t b;
1196
1197 switch ((int) ac)
1198 {
1199 case STACK_BOTTOM:
1200 goto done_undo;
1201 case CURS_RIGHT:
1202 edit_cursor_move (edit, 1);
1203 break;
1204 case CURS_LEFT:
1205 edit_cursor_move (edit, -1);
1206 break;
1207 case BACKSPACE:
1208 case BACKSPACE_BR:
1209 edit_backspace (edit, TRUE);
1210 break;
1211 case DELCHAR:
1212 case DELCHAR_BR:
1213 edit_delete (edit, TRUE);
1214 break;
1215 case COLUMN_ON:
1216 edit->column_highlight = 1;
1217 break;
1218 case COLUMN_OFF:
1219 edit->column_highlight = 0;
1220 break;
1221 default:
1222 break;
1223 }
1224 if (ac >= 256 && ac < 512)
1225 edit_insert_ahead (edit, ac - 256);
1226 if (ac >= 0 && ac < 256)
1227 edit_insert (edit, ac);
1228
1229 if (ac >= MARK_1 - 2 && ac < MARK_2 - 2)
1230 {
1231 edit->mark1 = ac - MARK_1;
1232 b = edit_buffer_get_bol (&edit->buffer, edit->mark1);
1233 edit->column1 = (long) edit_move_forward3 (edit, b, 0, edit->mark1);
1234 }
1235 if (ac >= MARK_2 - 2 && ac < MARK_CURS - 2)
1236 {
1237 edit->mark2 = ac - MARK_2;
1238 b = edit_buffer_get_bol (&edit->buffer, edit->mark2);
1239 edit->column2 = (long) edit_move_forward3 (edit, b, 0, edit->mark2);
1240 }
1241 else if (ac >= MARK_CURS - 2 && ac < KEY_PRESS)
1242 {
1243 edit->end_mark_curs = ac - MARK_CURS;
1244 }
1245 if (count++)
1246 edit->force |= REDRAW_PAGE;
1247 }
1248
1249 if (edit->start_display > ac - KEY_PRESS)
1250 {
1251 edit->start_line -=
1252 edit_buffer_count_lines (&edit->buffer, ac - KEY_PRESS, edit->start_display);
1253 edit->force |= REDRAW_PAGE;
1254 }
1255 else if (edit->start_display < ac - KEY_PRESS)
1256 {
1257 edit->start_line +=
1258 edit_buffer_count_lines (&edit->buffer, edit->start_display, ac - KEY_PRESS);
1259 edit->force |= REDRAW_PAGE;
1260 }
1261 edit->start_display = ac - KEY_PRESS;
1262 edit_update_curs_row (edit);
1263
1264 done_undo:
1265 edit->undo_stack_disable = 0;
1266 }
1267
1268
1269
1270 static void
1271 edit_do_redo (WEdit *edit)
1272 {
1273 long ac;
1274 long count = 0;
1275
1276 if (edit->redo_stack_reset)
1277 return;
1278
1279 edit->over_col = 0;
1280
1281 while ((ac = edit_pop_redo_action (edit)) < KEY_PRESS)
1282 {
1283 off_t b;
1284
1285 switch ((int) ac)
1286 {
1287 case STACK_BOTTOM:
1288 goto done_redo;
1289 case CURS_RIGHT:
1290 edit_cursor_move (edit, 1);
1291 break;
1292 case CURS_LEFT:
1293 edit_cursor_move (edit, -1);
1294 break;
1295 case BACKSPACE:
1296 edit_backspace (edit, TRUE);
1297 break;
1298 case DELCHAR:
1299 edit_delete (edit, TRUE);
1300 break;
1301 case COLUMN_ON:
1302 edit->column_highlight = 1;
1303 break;
1304 case COLUMN_OFF:
1305 edit->column_highlight = 0;
1306 break;
1307 default:
1308 break;
1309 }
1310 if (ac >= 256 && ac < 512)
1311 edit_insert_ahead (edit, ac - 256);
1312 if (ac >= 0 && ac < 256)
1313 edit_insert (edit, ac);
1314
1315 if (ac >= MARK_1 - 2 && ac < MARK_2 - 2)
1316 {
1317 edit->mark1 = ac - MARK_1;
1318 b = edit_buffer_get_bol (&edit->buffer, edit->mark1);
1319 edit->column1 = (long) edit_move_forward3 (edit, b, 0, edit->mark1);
1320 }
1321 else if (ac >= MARK_2 - 2 && ac < KEY_PRESS)
1322 {
1323 edit->mark2 = ac - MARK_2;
1324 b = edit_buffer_get_bol (&edit->buffer, edit->mark2);
1325 edit->column2 = (long) edit_move_forward3 (edit, b, 0, edit->mark2);
1326 }
1327
1328 if (count++ != 0)
1329 edit->force |= REDRAW_PAGE;
1330 }
1331
1332 if (edit->start_display > ac - KEY_PRESS)
1333 {
1334 edit->start_line -=
1335 edit_buffer_count_lines (&edit->buffer, ac - KEY_PRESS, edit->start_display);
1336 edit->force |= REDRAW_PAGE;
1337 }
1338 else if (edit->start_display < ac - KEY_PRESS)
1339 {
1340 edit->start_line +=
1341 edit_buffer_count_lines (&edit->buffer, edit->start_display, ac - KEY_PRESS);
1342 edit->force |= REDRAW_PAGE;
1343 }
1344 edit->start_display = ac - KEY_PRESS;
1345 edit_update_curs_row (edit);
1346
1347 done_redo:
1348 ;
1349 }
1350
1351
1352
1353 static void
1354 edit_group_undo (WEdit *edit)
1355 {
1356 long ac = KEY_PRESS;
1357 long cur_ac = KEY_PRESS;
1358
1359 while (ac != STACK_BOTTOM && ac == cur_ac)
1360 {
1361 cur_ac = get_prev_undo_action (edit);
1362 edit_do_undo (edit);
1363 ac = get_prev_undo_action (edit);
1364
1365
1366
1367 if (!edit_options.group_undo)
1368 ac = STACK_BOTTOM;
1369 }
1370 }
1371
1372
1373
1374 static void
1375 edit_delete_to_line_end (WEdit *edit)
1376 {
1377 while (edit_buffer_get_current_byte (&edit->buffer) != '\n' && edit->buffer.curs2 != 0)
1378 edit_delete (edit, TRUE);
1379 }
1380
1381
1382
1383 static void
1384 edit_delete_to_line_begin (WEdit *edit)
1385 {
1386 while (edit_buffer_get_previous_byte (&edit->buffer) != '\n' && edit->buffer.curs1 != 0)
1387 edit_backspace (edit, TRUE);
1388 }
1389
1390
1391
1392 static gboolean
1393 is_aligned_on_a_tab (WEdit *edit)
1394 {
1395 long curs_col;
1396
1397 edit_update_curs_col (edit);
1398 curs_col = edit->curs_col % (TAB_SIZE * space_width);
1399 return (curs_col == 0 || curs_col == (HALF_TAB_SIZE * space_width));
1400 }
1401
1402
1403
1404 static gboolean
1405 right_of_four_spaces (WEdit *edit)
1406 {
1407 int i;
1408 int ch = 0;
1409
1410 for (i = 1; i <= HALF_TAB_SIZE; i++)
1411 ch |= edit_buffer_get_byte (&edit->buffer, edit->buffer.curs1 - i);
1412
1413 return (ch == ' ' && is_aligned_on_a_tab (edit));
1414 }
1415
1416
1417
1418 static gboolean
1419 left_of_four_spaces (WEdit *edit)
1420 {
1421 int i, ch = 0;
1422
1423 for (i = 0; i < HALF_TAB_SIZE; i++)
1424 ch |= edit_buffer_get_byte (&edit->buffer, edit->buffer.curs1 + i);
1425
1426 return (ch == ' ' && is_aligned_on_a_tab (edit));
1427 }
1428
1429
1430
1431 static void
1432 edit_auto_indent (WEdit *edit)
1433 {
1434 off_t p;
1435
1436 p = edit->buffer.curs1;
1437
1438 p = edit_buffer_get_backward_offset (&edit->buffer, p, 1);
1439
1440 while (TRUE)
1441 {
1442 char c;
1443
1444 c = edit_buffer_get_byte (&edit->buffer, p++);
1445 if (!whitespace (c))
1446 break;
1447 edit_insert (edit, c);
1448 }
1449 }
1450
1451
1452
1453 static inline void
1454 edit_double_newline (WEdit *edit)
1455 {
1456 edit_insert (edit, '\n');
1457 if (edit_buffer_get_current_byte (&edit->buffer) == '\n'
1458 || edit_buffer_get_byte (&edit->buffer, edit->buffer.curs1 - 2) == '\n')
1459 return;
1460 edit->force |= REDRAW_PAGE;
1461 edit_insert (edit, '\n');
1462 }
1463
1464
1465
1466 static void
1467 insert_spaces_tab (WEdit *edit, gboolean half)
1468 {
1469 long i;
1470
1471 edit_update_curs_col (edit);
1472 i = TAB_SIZE * space_width;
1473 if (half)
1474 i /= 2;
1475 if (i != 0)
1476 for (i = ((edit->curs_col / i) + 1) * i - edit->curs_col; i > 0; i -= space_width)
1477 edit_insert (edit, ' ');
1478 }
1479
1480
1481
1482 static inline void
1483 edit_tab_cmd (WEdit *edit)
1484 {
1485 if (edit_options.fake_half_tabs && is_in_indent (&edit->buffer))
1486 {
1487
1488
1489
1490 if (edit_options.fill_tabs_with_spaces || !right_of_four_spaces (edit))
1491 insert_spaces_tab (edit, TRUE);
1492 else
1493 {
1494 int i;
1495
1496 for (i = 1; i <= HALF_TAB_SIZE; i++)
1497 edit_backspace (edit, TRUE);
1498 edit_insert (edit, '\t');
1499 }
1500 }
1501 else if (edit_options.fill_tabs_with_spaces)
1502 insert_spaces_tab (edit, FALSE);
1503 else
1504 edit_insert (edit, '\t');
1505 }
1506
1507
1508
1509 static void
1510 check_and_wrap_line (WEdit *edit)
1511 {
1512 off_t curs;
1513
1514 if (!edit_options.typewriter_wrap)
1515 return;
1516 edit_update_curs_col (edit);
1517 if (edit->curs_col < edit_options.word_wrap_line_length)
1518 return;
1519 curs = edit->buffer.curs1;
1520 while (TRUE)
1521 {
1522 int c;
1523
1524 curs--;
1525 c = edit_buffer_get_byte (&edit->buffer, curs);
1526 if (c == '\n' || curs <= 0)
1527 {
1528 edit_insert (edit, '\n');
1529 return;
1530 }
1531 if (whitespace (c))
1532 {
1533 off_t current = edit->buffer.curs1;
1534 edit_cursor_move (edit, curs - edit->buffer.curs1 + 1);
1535 edit_insert (edit, '\n');
1536 edit_cursor_move (edit, current - edit->buffer.curs1 + 1);
1537 return;
1538 }
1539 }
1540 }
1541
1542
1543
1544
1545
1546
1547
1548
1549
1550
1551
1552 static off_t
1553 edit_get_bracket (WEdit *edit, gboolean in_screen, unsigned long furthest_bracket_search)
1554 {
1555 const char *const b = "{}{[][()(", *p;
1556 int i = 1, inc = -1, c, d, n = 0;
1557 unsigned long j = 0;
1558 off_t q;
1559
1560 edit_update_curs_row (edit);
1561 c = edit_buffer_get_current_byte (&edit->buffer);
1562 p = strchr (b, c);
1563
1564 if (p == NULL || *p == '\0')
1565 return -1;
1566
1567 d = p[1];
1568
1569 if (strchr ("{[(", c) != NULL)
1570 inc = 1;
1571
1572 if (furthest_bracket_search == 0)
1573 furthest_bracket_search--;
1574 for (q = edit->buffer.curs1 + inc;; q += inc)
1575 {
1576 int a;
1577
1578
1579 if (q >= edit->buffer.size || q < 0)
1580 break;
1581 a = edit_buffer_get_byte (&edit->buffer, q);
1582
1583 if (j++ > furthest_bracket_search)
1584 break;
1585
1586 if (in_screen)
1587 {
1588 if (q < edit->start_display)
1589 break;
1590
1591 if (inc > 0 && a == '\n')
1592 if (n++ >= WIDGET (edit)->rect.lines - edit->curs_row)
1593 break;
1594 }
1595
1596 i += (a == c) - (a == d);
1597
1598 if (i == 0)
1599 return q;
1600 }
1601
1602 return -1;
1603 }
1604
1605
1606
1607 static inline void
1608 edit_goto_matching_bracket (WEdit *edit)
1609 {
1610 off_t q;
1611
1612 q = edit_get_bracket (edit, 0, 0);
1613 if (q >= 0)
1614 {
1615 edit->bracket = edit->buffer.curs1;
1616 edit->force |= REDRAW_PAGE;
1617 edit_cursor_move (edit, q - edit->buffer.curs1);
1618 }
1619 }
1620
1621
1622
1623 static void
1624 edit_move_block_to_right (WEdit *edit)
1625 {
1626 off_t start_mark, end_mark;
1627 long cur_bol, start_bol;
1628
1629 if (!eval_marks (edit, &start_mark, &end_mark))
1630 return;
1631
1632 start_bol = edit_buffer_get_bol (&edit->buffer, start_mark);
1633 cur_bol = edit_buffer_get_bol (&edit->buffer, end_mark - 1);
1634
1635 do
1636 {
1637 off_t b;
1638
1639 edit_cursor_move (edit, cur_bol - edit->buffer.curs1);
1640 if (!edit_line_is_blank (edit, edit->buffer.curs_line))
1641 {
1642 if (edit_options.fill_tabs_with_spaces)
1643 insert_spaces_tab (edit, edit_options.fake_half_tabs);
1644 else
1645 edit_insert (edit, '\t');
1646
1647 b = edit_buffer_get_bol (&edit->buffer, cur_bol);
1648 edit_cursor_move (edit, b - edit->buffer.curs1);
1649 }
1650
1651 if (cur_bol == 0)
1652 break;
1653
1654 cur_bol = edit_buffer_get_bol (&edit->buffer, cur_bol - 1);
1655 }
1656 while (cur_bol >= start_bol);
1657
1658 edit->force |= REDRAW_PAGE;
1659 }
1660
1661
1662
1663 static void
1664 edit_move_block_to_left (WEdit *edit)
1665 {
1666 off_t start_mark, end_mark;
1667 off_t cur_bol, start_bol;
1668
1669 if (!eval_marks (edit, &start_mark, &end_mark))
1670 return;
1671
1672 start_bol = edit_buffer_get_bol (&edit->buffer, start_mark);
1673 cur_bol = edit_buffer_get_bol (&edit->buffer, end_mark - 1);
1674
1675 do
1676 {
1677 int del_tab_width;
1678 int next_char;
1679
1680 edit_cursor_move (edit, cur_bol - edit->buffer.curs1);
1681
1682 del_tab_width = edit_options.fake_half_tabs ? HALF_TAB_SIZE : TAB_SIZE;
1683
1684 next_char = edit_buffer_get_current_byte (&edit->buffer);
1685 if (next_char == '\t')
1686 edit_delete (edit, TRUE);
1687 else if (next_char == ' ')
1688 {
1689 int i;
1690
1691 for (i = 0; i < del_tab_width; i++)
1692 {
1693 if (next_char == ' ')
1694 edit_delete (edit, TRUE);
1695 next_char = edit_buffer_get_current_byte (&edit->buffer);
1696 }
1697 }
1698
1699 if (cur_bol == 0)
1700 break;
1701
1702 cur_bol = edit_buffer_get_bol (&edit->buffer, cur_bol - 1);
1703 }
1704 while (cur_bol >= start_bol);
1705
1706 edit->force |= REDRAW_PAGE;
1707 }
1708
1709
1710
1711
1712
1713
1714
1715 static size_t
1716 edit_print_string (WEdit *e, const char *s)
1717 {
1718 size_t i;
1719
1720 for (i = 0; s[i] != '\0'; i++)
1721 edit_execute_cmd (e, CK_InsertChar, (unsigned char) s[i]);
1722 e->force |= REDRAW_COMPLETELY;
1723 edit_update_screen (e);
1724 return i;
1725 }
1726
1727
1728
1729 static off_t
1730 edit_insert_column_from_file (WEdit *edit, int file, off_t *start_pos, off_t *end_pos,
1731 long *col1, long *col2)
1732 {
1733 off_t cursor;
1734 long col;
1735 off_t blocklen = -1, width = 0;
1736 unsigned char *data;
1737
1738 cursor = edit->buffer.curs1;
1739 col = edit_get_col (edit);
1740 data = g_malloc0 (TEMP_BUF_LEN);
1741
1742 while ((blocklen = mc_read (file, (char *) data, TEMP_BUF_LEN)) > 0)
1743 {
1744 off_t i;
1745 char *pn;
1746
1747 pn = strchr ((char *) data, '\n');
1748 width = pn == NULL ? blocklen : pn - (char *) data;
1749
1750 for (i = 0; i < blocklen; i++)
1751 {
1752 if (data[i] != '\n')
1753 edit_insert (edit, data[i]);
1754 else
1755 {
1756 long l;
1757 off_t p;
1758
1759 if (edit_buffer_get_current_byte (&edit->buffer) != '\n')
1760 for (l = width - (edit_get_col (edit) - col); l > 0; l -= space_width)
1761 edit_insert (edit, ' ');
1762
1763 for (p = edit->buffer.curs1;; p++)
1764 {
1765 if (p == edit->buffer.size)
1766 {
1767 edit_cursor_move (edit, edit->buffer.size - edit->buffer.curs1);
1768 edit_insert_ahead (edit, '\n');
1769 p++;
1770 break;
1771 }
1772 if (edit_buffer_get_byte (&edit->buffer, p) == '\n')
1773 {
1774 p++;
1775 break;
1776 }
1777 }
1778
1779 edit_cursor_move (edit, edit_move_forward3 (edit, p, col, 0) - edit->buffer.curs1);
1780
1781 for (l = col - edit_get_col (edit); l >= space_width; l -= space_width)
1782 edit_insert (edit, ' ');
1783 }
1784 }
1785 }
1786 *col1 = col;
1787 *col2 = col + width;
1788 *start_pos = cursor;
1789 *end_pos = edit->buffer.curs1;
1790 edit_cursor_move (edit, cursor - edit->buffer.curs1);
1791 g_free (data);
1792
1793 return blocklen;
1794 }
1795
1796
1797
1798
1799
1800
1801
1802 void
1803 edit_user_menu (WEdit *edit, const char *menu_file, int selected_entry)
1804 {
1805 char *block_file;
1806 gboolean mark;
1807 off_t curs;
1808 off_t start_mark, end_mark;
1809 struct stat status;
1810 vfs_path_t *block_file_vpath;
1811
1812 block_file = mc_config_get_full_path (EDIT_HOME_BLOCK_FILE);
1813 block_file_vpath = vfs_path_from_str (block_file);
1814 curs = edit->buffer.curs1;
1815 mark = eval_marks (edit, &start_mark, &end_mark);
1816 if (mark)
1817 edit_save_block (edit, block_file, start_mark, end_mark);
1818
1819
1820 if (user_menu_cmd (CONST_WIDGET (edit), menu_file, selected_entry)
1821 && (mc_stat (block_file_vpath, &status) == 0) && (status.st_size != 0))
1822 {
1823 gboolean rc = TRUE;
1824 FILE *fd;
1825
1826
1827 if (mark)
1828 rc = edit_block_delete_cmd (edit);
1829
1830 if (rc)
1831 {
1832 off_t ins_len;
1833
1834 ins_len = edit_insert_file (edit, block_file_vpath);
1835 if (mark && ins_len > 0)
1836 edit_set_markers (edit, start_mark, start_mark + ins_len, 0, 0);
1837 }
1838
1839 fd = fopen (block_file, "w");
1840 if (fd != NULL)
1841 fclose (fd);
1842 }
1843 g_free (block_file);
1844 vfs_path_free (block_file_vpath, TRUE);
1845
1846 edit_cursor_move (edit, curs - edit->buffer.curs1);
1847 edit->force |= REDRAW_PAGE;
1848 widget_draw (WIDGET (edit));
1849 }
1850
1851
1852
1853 char *
1854 edit_get_write_filter (const vfs_path_t *write_name_vpath, const vfs_path_t *filename_vpath)
1855 {
1856 int i;
1857 const char *write_name;
1858 char *write_name_quoted;
1859 char *p = NULL;
1860
1861 i = edit_find_filter (filename_vpath);
1862 if (i < 0)
1863 return NULL;
1864
1865 write_name = vfs_path_get_last_path_str (write_name_vpath);
1866 write_name_quoted = name_quote (write_name, FALSE);
1867 if (write_name_quoted != NULL)
1868 {
1869 p = g_strdup_printf (all_filters[i].write, write_name_quoted);
1870 g_free (write_name_quoted);
1871 }
1872 return p;
1873 }
1874
1875
1876
1877
1878
1879
1880
1881
1882 off_t
1883 edit_write_stream (WEdit *edit, FILE *f)
1884 {
1885 long i;
1886
1887 if (edit->lb == LB_ASIS)
1888 {
1889 for (i = 0; i < edit->buffer.size; i++)
1890 if (fputc (edit_buffer_get_byte (&edit->buffer, i), f) < 0)
1891 break;
1892 return i;
1893 }
1894
1895
1896 for (i = 0; i < edit->buffer.size; i++)
1897 {
1898 unsigned char c;
1899
1900 c = edit_buffer_get_byte (&edit->buffer, i);
1901 if (!(c == '\n' || c == '\r'))
1902 {
1903
1904 if (fputc (c, f) < 0)
1905 return i;
1906 }
1907 else
1908 {
1909 unsigned char c1;
1910
1911 c1 = edit_buffer_get_byte (&edit->buffer, i + 1);
1912
1913 switch (edit->lb)
1914 {
1915 case LB_UNIX:
1916
1917 if (fputc ('\n', f) < 0)
1918 return i;
1919
1920 i++;
1921
1922 if (c == '\r' && c1 == '\n')
1923
1924 break;
1925
1926 if (c == '\r' && c1 == '\r')
1927 {
1928
1929 if (fputc ('\n', f) < 0)
1930 return i;
1931 break;
1932 }
1933
1934 if (fputc (c1, f) < 0)
1935 return i;
1936 break;
1937
1938 case LB_WIN:
1939
1940 if (fputc ('\r', f) < 0 || fputc ('\n', f) < 0)
1941 return i;
1942
1943 if (c == '\r' && c1 == '\n')
1944
1945 i++;
1946 break;
1947
1948 case LB_MAC:
1949
1950 if (fputc ('\r', f) < 0)
1951 return i;
1952
1953 i++;
1954
1955 if (c == '\r' && c1 == '\n')
1956
1957 break;
1958
1959 if (c == '\n' && c1 == '\n')
1960 {
1961
1962 if (fputc ('\r', f) < 0)
1963 return i;
1964 break;
1965 }
1966
1967 if (fputc (c1, f) < 0)
1968 return i;
1969 break;
1970 case LB_ASIS:
1971 default:
1972 break;
1973 }
1974 }
1975 }
1976
1977 return edit->buffer.size;
1978 }
1979
1980
1981
1982 gboolean
1983 is_break_char (char c)
1984 {
1985 return (isspace (c) || strchr ("{}[]()<>=|/\\!?~-+`'\",.;:#$%^&*", c) != NULL);
1986 }
1987
1988
1989
1990
1991 off_t
1992 edit_insert_file (WEdit *edit, const vfs_path_t *filename_vpath)
1993 {
1994 char *p;
1995 off_t current;
1996 off_t ins_len = 0;
1997
1998 p = edit_get_filter (filename_vpath);
1999 current = edit->buffer.curs1;
2000
2001 if (p != NULL)
2002 {
2003 FILE *f;
2004
2005 f = (FILE *) popen (p, "r");
2006 if (f != NULL)
2007 {
2008 edit_insert_stream (edit, f);
2009
2010
2011 if (!edit_options.cursor_after_inserted_block)
2012 {
2013 ins_len = edit->buffer.curs1 - current;
2014 edit_cursor_move (edit, -ins_len);
2015 }
2016 if (pclose (f) > 0)
2017 {
2018 char *errmsg;
2019
2020 errmsg = g_strdup_printf (_("Error reading from pipe: %s"), p);
2021 edit_error_dialog (_("Error"), errmsg);
2022 g_free (errmsg);
2023 ins_len = -1;
2024 }
2025 }
2026 else
2027 {
2028 char *errmsg;
2029
2030 errmsg = g_strdup_printf (_("Cannot open pipe for reading: %s"), p);
2031 edit_error_dialog (_("Error"), errmsg);
2032 g_free (errmsg);
2033 ins_len = -1;
2034 }
2035 g_free (p);
2036 }
2037 else
2038 {
2039 int file;
2040 off_t blocklen;
2041 gboolean vertical_insertion = FALSE;
2042 char *buf;
2043
2044 file = mc_open (filename_vpath, O_RDONLY | O_BINARY);
2045 if (file == -1)
2046 return -1;
2047
2048 buf = g_malloc0 (TEMP_BUF_LEN);
2049 blocklen = mc_read (file, buf, sizeof (VERTICAL_MAGIC));
2050 if (blocklen > 0)
2051 {
2052
2053 if (memcmp (buf, VERTICAL_MAGIC, sizeof (VERTICAL_MAGIC)) == 0)
2054 vertical_insertion = TRUE;
2055 else
2056 mc_lseek (file, 0, SEEK_SET);
2057 }
2058
2059 if (vertical_insertion)
2060 {
2061 off_t mark1, mark2;
2062 long c1, c2;
2063
2064 blocklen = edit_insert_column_from_file (edit, file, &mark1, &mark2, &c1, &c2);
2065 edit_set_markers (edit, edit->buffer.curs1, mark2, c1, c2);
2066
2067
2068 if (!edit_options.persistent_selections && edit->modified)
2069 {
2070 if (!edit->column_highlight)
2071 edit_push_undo_action (edit, COLUMN_OFF);
2072 edit->column_highlight = 1;
2073 }
2074 }
2075 else
2076 {
2077 off_t i;
2078
2079 while ((blocklen = mc_read (file, (char *) buf, TEMP_BUF_LEN)) > 0)
2080 {
2081 for (i = 0; i < blocklen; i++)
2082 edit_insert (edit, buf[i]);
2083 }
2084
2085 if (!edit_options.persistent_selections && edit->modified)
2086 {
2087 edit_set_markers (edit, edit->buffer.curs1, current, 0, 0);
2088 if (edit->column_highlight)
2089 edit_push_undo_action (edit, COLUMN_ON);
2090 edit->column_highlight = 0;
2091 }
2092
2093
2094 if (!edit_options.cursor_after_inserted_block)
2095 {
2096 ins_len = edit->buffer.curs1 - current;
2097 edit_cursor_move (edit, -ins_len);
2098 }
2099 }
2100
2101 edit->force |= REDRAW_PAGE;
2102 g_free (buf);
2103 mc_close (file);
2104 if (blocklen != 0)
2105 ins_len = 0;
2106 }
2107
2108 return ins_len;
2109 }
2110
2111
2112
2113
2114
2115
2116
2117
2118
2119
2120 WEdit *
2121 edit_init (WEdit *edit, const WRect *r, const edit_arg_t *arg)
2122 {
2123 gboolean to_free = FALSE;
2124 long line;
2125
2126 auto_syntax = TRUE;
2127 edit_options.line_state_width = edit_options.line_state ? LINE_STATE_WIDTH : 0;
2128
2129 if (edit != NULL)
2130 {
2131 gboolean fullscreen;
2132 WRect loc_prev;
2133
2134
2135 fullscreen = edit->fullscreen;
2136 loc_prev = edit->loc_prev;
2137
2138 edit_purge_widget (edit);
2139
2140
2141 edit->fullscreen = fullscreen;
2142 edit->loc_prev = loc_prev;
2143 }
2144 else
2145 {
2146 Widget *w;
2147
2148 edit = g_malloc0 (sizeof (WEdit));
2149 to_free = TRUE;
2150
2151 w = WIDGET (edit);
2152 widget_init (w, r, NULL, NULL);
2153 w->options |= WOP_SELECTABLE | WOP_TOP_SELECT | WOP_WANT_CURSOR;
2154 w->keymap = editor_map;
2155 w->ext_keymap = editor_x_map;
2156 edit->fullscreen = TRUE;
2157 edit_save_size (edit);
2158 }
2159
2160 edit->drag_state = MCEDIT_DRAG_NONE;
2161
2162 edit->stat1.st_mode = S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH;
2163 edit->stat1.st_uid = getuid ();
2164 edit->stat1.st_gid = getgid ();
2165 edit->stat1.st_mtime = 0;
2166
2167 if (arg != NULL)
2168 edit->attrs_ok = (mc_fgetflags (arg->file_vpath, &edit->attrs) == 0);
2169 else
2170 edit->attrs_ok = FALSE;
2171
2172 edit->over_col = 0;
2173 edit->bracket = -1;
2174 edit->last_bracket = -1;
2175 edit->force |= REDRAW_PAGE;
2176
2177
2178 if (arg != NULL)
2179 {
2180 edit_set_filename (edit, arg->file_vpath);
2181 line = arg->line_number;
2182 }
2183 else
2184 {
2185 edit_set_filename (edit, NULL);
2186 line = 0;
2187 }
2188
2189 edit->undo_stack_size = START_STACK_SIZE;
2190 edit->undo_stack_size_mask = START_STACK_SIZE - 1;
2191 edit->undo_stack = g_malloc0 ((edit->undo_stack_size + 10) * sizeof (long));
2192
2193 edit->redo_stack_size = START_STACK_SIZE;
2194 edit->redo_stack_size_mask = START_STACK_SIZE - 1;
2195 edit->redo_stack = g_malloc0 ((edit->redo_stack_size + 10) * sizeof (long));
2196
2197 #ifdef HAVE_CHARSET
2198 edit->utf8 = FALSE;
2199 edit->converter = str_cnv_from_term;
2200 edit_set_codeset (edit);
2201 #endif
2202
2203 if (!edit_load_file (edit))
2204 {
2205
2206 if (to_free)
2207 g_free (edit);
2208 return NULL;
2209 }
2210
2211 edit->loading_done = 1;
2212 edit->modified = 0;
2213 edit->locked = 0;
2214 edit_load_syntax (edit, NULL, NULL);
2215 edit_get_syntax_color (edit, -1);
2216
2217
2218 if ((line == 0) && edit_options.save_position)
2219 edit_load_position (edit, TRUE);
2220 else
2221 {
2222 edit_load_position (edit, FALSE);
2223 if (line <= 0)
2224 line = 1;
2225 edit_move_display (edit, line - 1);
2226 edit_move_to_line (edit, line - 1);
2227 }
2228
2229 edit_load_macro_cmd (edit);
2230
2231 return edit;
2232 }
2233
2234
2235
2236
2237 gboolean
2238 edit_clean (WEdit *edit)
2239 {
2240 if (edit == NULL)
2241 return FALSE;
2242
2243
2244 if (edit->locked)
2245 (void) unlock_file (edit->filename_vpath);
2246
2247
2248 if (edit_options.save_position)
2249 edit_save_position (edit);
2250 else if (edit->serialized_bookmarks != NULL)
2251 g_array_free (edit->serialized_bookmarks, TRUE);
2252
2253
2254 if (edit->delete_file)
2255 unlink (vfs_path_get_last_path_str (edit->filename_vpath));
2256
2257 edit_free_syntax_rules (edit);
2258 book_mark_flush (edit, -1);
2259
2260 edit_buffer_clean (&edit->buffer);
2261
2262 g_free (edit->undo_stack);
2263 g_free (edit->redo_stack);
2264 vfs_path_free (edit->filename_vpath, TRUE);
2265 vfs_path_free (edit->dir_vpath, TRUE);
2266 edit_search_deinit (edit);
2267
2268 #ifdef HAVE_CHARSET
2269 if (edit->converter != str_cnv_from_term)
2270 str_close_conv (edit->converter);
2271 #endif
2272
2273 edit_purge_widget (edit);
2274
2275 return TRUE;
2276 }
2277
2278
2279
2280
2281
2282
2283
2284
2285
2286
2287 gboolean
2288 edit_reload_line (WEdit *edit, const edit_arg_t *arg)
2289 {
2290 Widget *w = WIDGET (edit);
2291 WEdit *e;
2292
2293 e = g_malloc0 (sizeof (WEdit));
2294 *WIDGET (e) = *w;
2295
2296 e->fullscreen = edit->fullscreen;
2297 e->loc_prev = edit->loc_prev;
2298
2299 if (edit_init (e, &w->rect, arg) == NULL)
2300 {
2301 g_free (e);
2302 return FALSE;
2303 }
2304
2305 edit_clean (edit);
2306 memcpy (edit, e, sizeof (*edit));
2307 g_free (e);
2308
2309 return TRUE;
2310 }
2311
2312
2313
2314 #ifdef HAVE_CHARSET
2315 void
2316 edit_set_codeset (WEdit *edit)
2317 {
2318 const char *cp_id;
2319
2320 cp_id =
2321 get_codepage_id (mc_global.source_codepage >=
2322 0 ? mc_global.source_codepage : mc_global.display_codepage);
2323
2324 if (cp_id != NULL)
2325 {
2326 GIConv conv;
2327 conv = str_crt_conv_from (cp_id);
2328 if (conv != INVALID_CONV)
2329 {
2330 if (edit->converter != str_cnv_from_term)
2331 str_close_conv (edit->converter);
2332 edit->converter = conv;
2333 }
2334 }
2335
2336 if (cp_id != NULL)
2337 edit->utf8 = str_isutf8 (cp_id);
2338 }
2339 #endif
2340
2341
2342
2343
2344
2345
2346
2347
2348
2349
2350
2351
2352
2353
2354
2355
2356
2357
2358
2359
2360
2361
2362
2363
2364
2365
2366
2367
2368
2369
2370
2371
2372
2373
2374
2375
2376
2377
2378
2379
2380
2381
2382
2383
2384
2385
2386
2387 void
2388 edit_push_undo_action (WEdit *edit, long c)
2389 {
2390 unsigned long sp = edit->undo_stack_pointer;
2391 unsigned long spm1;
2392
2393
2394 if (sp > edit->undo_stack_size - 10)
2395 {
2396 if (max_undo < 256)
2397 max_undo = 256;
2398 if (edit->undo_stack_size < (unsigned long) max_undo)
2399 {
2400 long *t;
2401
2402 t = g_realloc (edit->undo_stack, (edit->undo_stack_size * 2 + 10) * sizeof (long));
2403 if (t != NULL)
2404 {
2405 edit->undo_stack = t;
2406 edit->undo_stack_size <<= 1;
2407 edit->undo_stack_size_mask = edit->undo_stack_size - 1;
2408 }
2409 }
2410 }
2411 spm1 = (edit->undo_stack_pointer - 1) & edit->undo_stack_size_mask;
2412 if (edit->undo_stack_disable)
2413 {
2414 edit_push_redo_action (edit, KEY_PRESS);
2415 edit_push_redo_action (edit, c);
2416 return;
2417 }
2418
2419 if (edit->redo_stack_reset)
2420 edit->redo_stack_bottom = edit->redo_stack_pointer = 0;
2421
2422 if (edit->undo_stack_bottom != sp
2423 && spm1 != edit->undo_stack_bottom
2424 && ((sp - 2) & edit->undo_stack_size_mask) != edit->undo_stack_bottom)
2425 {
2426 long d;
2427
2428 if (edit->undo_stack[spm1] < 0)
2429 {
2430 d = edit->undo_stack[(sp - 2) & edit->undo_stack_size_mask];
2431 if (d == c && edit->undo_stack[spm1] > -1000000000)
2432 {
2433 if (c < KEY_PRESS)
2434 edit->undo_stack[spm1]--;
2435 return;
2436 }
2437 }
2438 else
2439 {
2440 d = edit->undo_stack[spm1];
2441 if (d == c)
2442 {
2443 if (c >= KEY_PRESS)
2444 return;
2445 edit->undo_stack[sp] = -2;
2446 goto check_bottom;
2447 }
2448 }
2449 }
2450 edit->undo_stack[sp] = c;
2451
2452 check_bottom:
2453 edit->undo_stack_pointer = (edit->undo_stack_pointer + 1) & edit->undo_stack_size_mask;
2454
2455
2456
2457
2458 c = (edit->undo_stack_pointer + 2) & edit->undo_stack_size_mask;
2459 if ((unsigned long) c == edit->undo_stack_bottom ||
2460 (((unsigned long) c + 1) & edit->undo_stack_size_mask) == edit->undo_stack_bottom)
2461 do
2462 {
2463 edit->undo_stack_bottom = (edit->undo_stack_bottom + 1) & edit->undo_stack_size_mask;
2464 }
2465 while (edit->undo_stack[edit->undo_stack_bottom] < KEY_PRESS
2466 && edit->undo_stack_bottom != edit->undo_stack_pointer);
2467
2468
2469 if (edit->undo_stack_pointer != edit->undo_stack_bottom
2470 && edit->undo_stack[edit->undo_stack_bottom] < KEY_PRESS)
2471 {
2472 edit->undo_stack_bottom = edit->undo_stack_pointer = 0;
2473 }
2474 }
2475
2476
2477
2478 void
2479 edit_push_redo_action (WEdit *edit, long c)
2480 {
2481 unsigned long sp = edit->redo_stack_pointer;
2482 unsigned long spm1;
2483
2484 if (sp > edit->redo_stack_size - 10)
2485 {
2486 if (max_undo < 256)
2487 max_undo = 256;
2488 if (edit->redo_stack_size < (unsigned long) max_undo)
2489 {
2490 long *t;
2491
2492 t = g_realloc (edit->redo_stack, (edit->redo_stack_size * 2 + 10) * sizeof (long));
2493 if (t != NULL)
2494 {
2495 edit->redo_stack = t;
2496 edit->redo_stack_size <<= 1;
2497 edit->redo_stack_size_mask = edit->redo_stack_size - 1;
2498 }
2499 }
2500 }
2501 spm1 = (edit->redo_stack_pointer - 1) & edit->redo_stack_size_mask;
2502
2503 if (edit->redo_stack_bottom != sp
2504 && spm1 != edit->redo_stack_bottom
2505 && ((sp - 2) & edit->redo_stack_size_mask) != edit->redo_stack_bottom)
2506 {
2507 long d;
2508
2509 if (edit->redo_stack[spm1] < 0)
2510 {
2511 d = edit->redo_stack[(sp - 2) & edit->redo_stack_size_mask];
2512 if (d == c && edit->redo_stack[spm1] > -1000000000)
2513 {
2514 if (c < KEY_PRESS)
2515 edit->redo_stack[spm1]--;
2516 return;
2517 }
2518 }
2519 else
2520 {
2521 d = edit->redo_stack[spm1];
2522 if (d == c)
2523 {
2524 if (c >= KEY_PRESS)
2525 return;
2526 edit->redo_stack[sp] = -2;
2527 goto redo_check_bottom;
2528 }
2529 }
2530 }
2531 edit->redo_stack[sp] = c;
2532
2533 redo_check_bottom:
2534 edit->redo_stack_pointer = (edit->redo_stack_pointer + 1) & edit->redo_stack_size_mask;
2535
2536
2537
2538
2539 c = (edit->redo_stack_pointer + 2) & edit->redo_stack_size_mask;
2540 if ((unsigned long) c == edit->redo_stack_bottom ||
2541 (((unsigned long) c + 1) & edit->redo_stack_size_mask) == edit->redo_stack_bottom)
2542 do
2543 {
2544 edit->redo_stack_bottom = (edit->redo_stack_bottom + 1) & edit->redo_stack_size_mask;
2545 }
2546 while (edit->redo_stack[edit->redo_stack_bottom] < KEY_PRESS
2547 && edit->redo_stack_bottom != edit->redo_stack_pointer);
2548
2549
2550
2551
2552
2553
2554
2555 if (edit->redo_stack_pointer != edit->redo_stack_bottom
2556 && edit->redo_stack[edit->redo_stack_bottom] < KEY_PRESS)
2557 edit->redo_stack_bottom = edit->redo_stack_pointer = 0;
2558 }
2559
2560
2561
2562
2563
2564
2565 void
2566 edit_insert (WEdit *edit, int c)
2567 {
2568
2569 if (edit->buffer.curs1 < edit->start_display)
2570 {
2571 edit->start_display++;
2572 if (c == '\n')
2573 edit->start_line++;
2574 }
2575
2576
2577 if (edit->loading_done)
2578 edit_modification (edit);
2579
2580
2581 if (c == '\n')
2582 {
2583 book_mark_inc (edit, edit->buffer.curs_line);
2584 edit->buffer.curs_line++;
2585 edit->buffer.lines++;
2586 edit->force |= REDRAW_LINE_ABOVE | REDRAW_AFTER_CURSOR;
2587 }
2588
2589
2590
2591 if (c > 32)
2592 edit_push_undo_action (edit, BACKSPACE);
2593 else
2594 edit_push_undo_action (edit, BACKSPACE_BR);
2595
2596 edit->mark1 += (edit->mark1 > edit->buffer.curs1) ? 1 : 0;
2597 edit->mark2 += (edit->mark2 > edit->buffer.curs1) ? 1 : 0;
2598 edit->last_get_rule += (edit->last_get_rule > edit->buffer.curs1) ? 1 : 0;
2599
2600 edit_buffer_insert (&edit->buffer, c);
2601 }
2602
2603
2604
2605
2606 void
2607 edit_insert_ahead (WEdit *edit, int c)
2608 {
2609 if (edit->buffer.curs1 < edit->start_display)
2610 {
2611 edit->start_display++;
2612 if (c == '\n')
2613 edit->start_line++;
2614 }
2615 edit_modification (edit);
2616 if (c == '\n')
2617 {
2618 book_mark_inc (edit, edit->buffer.curs_line);
2619 edit->buffer.lines++;
2620 edit->force |= REDRAW_AFTER_CURSOR;
2621 }
2622
2623 if (c > 32)
2624 edit_push_undo_action (edit, DELCHAR);
2625 else
2626 edit_push_undo_action (edit, DELCHAR_BR);
2627
2628 edit->mark1 += (edit->mark1 >= edit->buffer.curs1) ? 1 : 0;
2629 edit->mark2 += (edit->mark2 >= edit->buffer.curs1) ? 1 : 0;
2630 edit->last_get_rule += (edit->last_get_rule >= edit->buffer.curs1) ? 1 : 0;
2631
2632 edit_buffer_insert_ahead (&edit->buffer, c);
2633 }
2634
2635
2636
2637 void
2638 edit_insert_over (WEdit *edit)
2639 {
2640 long i;
2641
2642 for (i = 0; i < edit->over_col; i++)
2643 edit_insert (edit, ' ');
2644
2645 edit->over_col = 0;
2646 }
2647
2648
2649
2650 int
2651 edit_delete (WEdit *edit, gboolean byte_delete)
2652 {
2653 int p = 0;
2654 int char_length = 1;
2655 int i;
2656
2657 if (edit->buffer.curs2 == 0)
2658 return 0;
2659
2660 #ifdef HAVE_CHARSET
2661
2662 if (edit->utf8 && !byte_delete)
2663 {
2664 edit_buffer_get_utf (&edit->buffer, edit->buffer.curs1, &char_length);
2665 if (char_length < 1)
2666 char_length = 1;
2667 }
2668 #else
2669 (void) byte_delete;
2670 #endif
2671
2672 if (edit->mark2 != edit->mark1)
2673 edit_push_markers (edit);
2674
2675 for (i = 1; i <= char_length; i++)
2676 {
2677 if (edit->mark1 > edit->buffer.curs1)
2678 {
2679 edit->mark1--;
2680 edit->end_mark_curs--;
2681 }
2682 if (edit->mark2 > edit->buffer.curs1)
2683 edit->mark2--;
2684 if (edit->last_get_rule > edit->buffer.curs1)
2685 edit->last_get_rule--;
2686
2687 p = edit_buffer_delete (&edit->buffer);
2688
2689 edit_push_undo_action (edit, p + 256);
2690 }
2691
2692 edit_modification (edit);
2693 if (p == '\n')
2694 {
2695 book_mark_dec (edit, edit->buffer.curs_line);
2696 edit->buffer.lines--;
2697 edit->force |= REDRAW_AFTER_CURSOR;
2698 }
2699 if (edit->buffer.curs1 < edit->start_display)
2700 {
2701 edit->start_display--;
2702 if (p == '\n')
2703 edit->start_line--;
2704 }
2705
2706 return p;
2707 }
2708
2709
2710
2711 int
2712 edit_backspace (WEdit *edit, gboolean byte_delete)
2713 {
2714 int p = 0;
2715 int char_length = 1;
2716 int i;
2717
2718 if (edit->buffer.curs1 == 0)
2719 return 0;
2720
2721 if (edit->mark2 != edit->mark1)
2722 edit_push_markers (edit);
2723
2724 #ifdef HAVE_CHARSET
2725 if (edit->utf8 && !byte_delete)
2726 {
2727 edit_buffer_get_prev_utf (&edit->buffer, edit->buffer.curs1, &char_length);
2728 if (char_length < 1)
2729 char_length = 1;
2730 }
2731 #else
2732 (void) byte_delete;
2733 #endif
2734
2735 for (i = 1; i <= char_length; i++)
2736 {
2737 if (edit->mark1 >= edit->buffer.curs1)
2738 {
2739 edit->mark1--;
2740 edit->end_mark_curs--;
2741 }
2742 if (edit->mark2 >= edit->buffer.curs1)
2743 edit->mark2--;
2744 if (edit->last_get_rule >= edit->buffer.curs1)
2745 edit->last_get_rule--;
2746
2747 p = edit_buffer_backspace (&edit->buffer);
2748
2749 edit_push_undo_action (edit, p);
2750 }
2751 edit_modification (edit);
2752 if (p == '\n')
2753 {
2754 book_mark_dec (edit, edit->buffer.curs_line);
2755 edit->buffer.curs_line--;
2756 edit->buffer.lines--;
2757 edit->force |= REDRAW_AFTER_CURSOR;
2758 }
2759
2760 if (edit->buffer.curs1 < edit->start_display)
2761 {
2762 edit->start_display--;
2763 if (p == '\n')
2764 edit->start_line--;
2765 }
2766
2767 return p;
2768 }
2769
2770
2771
2772
2773 void
2774 edit_cursor_move (WEdit *edit, off_t increment)
2775 {
2776 if (increment < 0)
2777 {
2778 for (; increment < 0 && edit->buffer.curs1 != 0; increment++)
2779 {
2780 int c;
2781
2782 edit_push_undo_action (edit, CURS_RIGHT);
2783
2784 c = edit_buffer_get_previous_byte (&edit->buffer);
2785 edit_buffer_insert_ahead (&edit->buffer, c);
2786 c = edit_buffer_backspace (&edit->buffer);
2787 if (c == '\n')
2788 {
2789 edit->buffer.curs_line--;
2790 edit->force |= REDRAW_LINE_BELOW;
2791 }
2792 }
2793 }
2794 else
2795 {
2796 for (; increment > 0 && edit->buffer.curs2 != 0; increment--)
2797 {
2798 int c;
2799
2800 edit_push_undo_action (edit, CURS_LEFT);
2801
2802 c = edit_buffer_get_current_byte (&edit->buffer);
2803 edit_buffer_insert (&edit->buffer, c);
2804 c = edit_buffer_delete (&edit->buffer);
2805 if (c == '\n')
2806 {
2807 edit->buffer.curs_line++;
2808 edit->force |= REDRAW_LINE_ABOVE;
2809 }
2810 }
2811 }
2812 }
2813
2814
2815
2816
2817
2818 off_t
2819 edit_move_forward3 (const WEdit *edit, off_t current, long cols, off_t upto)
2820 {
2821 off_t p, q;
2822 long col;
2823
2824 if (upto != 0)
2825 {
2826 q = upto;
2827 cols = -10;
2828 }
2829 else
2830 q = edit->buffer.size + 2;
2831
2832 for (col = 0, p = current; p < q; p++)
2833 {
2834 int c, orig_c;
2835
2836 if (cols != -10)
2837 {
2838 if (col == cols)
2839 return p;
2840 if (col > cols)
2841 return p - 1;
2842 }
2843
2844 orig_c = c = edit_buffer_get_byte (&edit->buffer, p);
2845
2846 #ifdef HAVE_CHARSET
2847 if (edit->utf8)
2848 {
2849 int utf_ch;
2850 int char_length = 1;
2851
2852 utf_ch = edit_buffer_get_utf (&edit->buffer, p, &char_length);
2853 if (mc_global.utf8_display)
2854 {
2855 if (char_length > 1)
2856 col -= char_length - 1;
2857 if (g_unichar_iswide (utf_ch))
2858 col++;
2859 }
2860 else if (char_length > 1 && g_unichar_isprint (utf_ch))
2861 col -= char_length - 1;
2862 }
2863
2864 c = convert_to_display_c (c);
2865 #endif
2866
2867 if (c == '\n')
2868 return (upto != 0 ? (off_t) col : p);
2869 if (c == '\t')
2870 col += TAB_SIZE - col % TAB_SIZE;
2871 else if ((c < 32 || c == 127) && (orig_c == c
2872 #ifdef HAVE_CHARSET
2873 || (!mc_global.utf8_display && !edit->utf8)
2874 #endif
2875 ))
2876
2877
2878 col += 2;
2879 else
2880 col++;
2881 }
2882 return (off_t) col;
2883 }
2884
2885
2886
2887
2888 off_t
2889 edit_get_cursor_offset (const WEdit *edit)
2890 {
2891 return edit->buffer.curs1;
2892 }
2893
2894
2895
2896
2897 long
2898 edit_get_col (const WEdit *edit)
2899 {
2900 off_t b;
2901
2902 b = edit_buffer_get_current_bol (&edit->buffer);
2903 return (long) edit_move_forward3 (edit, b, 0, edit->buffer.curs1);
2904 }
2905
2906
2907
2908
2909
2910 void
2911 edit_update_curs_row (WEdit *edit)
2912 {
2913 edit->curs_row = edit->buffer.curs_line - edit->start_line;
2914 }
2915
2916
2917
2918 void
2919 edit_update_curs_col (WEdit *edit)
2920 {
2921 off_t b;
2922
2923 b = edit_buffer_get_current_bol (&edit->buffer);
2924 edit->curs_col = (long) edit_move_forward3 (edit, b, 0, edit->buffer.curs1);
2925 }
2926
2927
2928
2929 long
2930 edit_get_curs_col (const WEdit *edit)
2931 {
2932 return edit->curs_col;
2933 }
2934
2935
2936
2937
2938 void
2939 edit_scroll_upward (WEdit *edit, long i)
2940 {
2941 long lines_above = edit->start_line;
2942
2943 if (i > lines_above)
2944 i = lines_above;
2945 if (i != 0)
2946 {
2947 edit->start_line -= i;
2948 edit->start_display =
2949 edit_buffer_get_backward_offset (&edit->buffer, edit->start_display, i);
2950 edit->force |= REDRAW_PAGE;
2951 edit->force &= (0xfff - REDRAW_CHAR_ONLY);
2952 }
2953 edit_update_curs_row (edit);
2954 }
2955
2956
2957
2958 void
2959 edit_scroll_downward (WEdit *edit, long i)
2960 {
2961 long lines_below;
2962
2963 lines_below = edit->buffer.lines - edit->start_line - (WIDGET (edit)->rect.lines - 1);
2964 if (lines_below > 0)
2965 {
2966 if (i > lines_below)
2967 i = lines_below;
2968 edit->start_line += i;
2969 edit->start_display =
2970 edit_buffer_get_forward_offset (&edit->buffer, edit->start_display, i, 0);
2971 edit->force |= REDRAW_PAGE;
2972 edit->force &= (0xfff - REDRAW_CHAR_ONLY);
2973 }
2974 edit_update_curs_row (edit);
2975 }
2976
2977
2978
2979 void
2980 edit_scroll_right (WEdit *edit, long i)
2981 {
2982 edit->force |= REDRAW_PAGE;
2983 edit->force &= (0xfff - REDRAW_CHAR_ONLY);
2984 edit->start_col -= i;
2985 }
2986
2987
2988
2989 void
2990 edit_scroll_left (WEdit *edit, long i)
2991 {
2992 if (edit->start_col)
2993 {
2994 edit->start_col += i;
2995 if (edit->start_col > 0)
2996 edit->start_col = 0;
2997 edit->force |= REDRAW_PAGE;
2998 edit->force &= (0xfff - REDRAW_CHAR_ONLY);
2999 }
3000 }
3001
3002
3003
3004
3005
3006 void
3007 edit_move_to_prev_col (WEdit *edit, off_t p)
3008 {
3009 long prev = edit->prev_col;
3010 long over = edit->over_col;
3011 off_t b;
3012
3013 edit_cursor_move (edit,
3014 edit_move_forward3 (edit, p, prev + edit->over_col, 0) - edit->buffer.curs1);
3015
3016 if (edit_options.cursor_beyond_eol)
3017 {
3018 off_t e;
3019 long line_len;
3020
3021 b = edit_buffer_get_current_bol (&edit->buffer);
3022 e = edit_buffer_get_current_eol (&edit->buffer);
3023 line_len = (long) edit_move_forward3 (edit, b, 0, e);
3024 if (line_len < prev + edit->over_col)
3025 {
3026 edit->over_col = prev + over - line_len;
3027 edit->prev_col = line_len;
3028 edit->curs_col = line_len;
3029 }
3030 else
3031 {
3032 edit->curs_col = prev + over;
3033 edit->prev_col = edit->curs_col;
3034 edit->over_col = 0;
3035 }
3036 }
3037 else
3038 {
3039 edit->over_col = 0;
3040 if (edit_options.fake_half_tabs && is_in_indent (&edit->buffer))
3041 {
3042 long fake_half_tabs;
3043
3044 edit_update_curs_col (edit);
3045
3046 fake_half_tabs = HALF_TAB_SIZE * space_width;
3047 if (fake_half_tabs != 0 && edit->curs_col % fake_half_tabs != 0)
3048 {
3049 long q;
3050
3051 q = edit->curs_col;
3052 edit->curs_col -= (edit->curs_col % fake_half_tabs);
3053 p = edit_buffer_get_current_bol (&edit->buffer);
3054 b = edit_move_forward3 (edit, p, edit->curs_col, 0);
3055 edit_cursor_move (edit, b - edit->buffer.curs1);
3056 if (!left_of_four_spaces (edit))
3057 {
3058 b = edit_move_forward3 (edit, p, q, 0);
3059 edit_cursor_move (edit, b - edit->buffer.curs1);
3060 }
3061 }
3062 }
3063 }
3064 }
3065
3066
3067
3068
3069
3070
3071
3072
3073
3074
3075 gboolean
3076 edit_line_is_blank (WEdit *edit, long line)
3077 {
3078 return is_blank (&edit->buffer, edit_find_line (edit, line));
3079 }
3080
3081
3082
3083
3084 void
3085 edit_move_to_line (WEdit *e, long line)
3086 {
3087 if (line < e->buffer.curs_line)
3088 edit_move_up (e, e->buffer.curs_line - line, FALSE);
3089 else
3090 edit_move_down (e, line - e->buffer.curs_line, FALSE);
3091 edit_scroll_screen_over_cursor (e);
3092 }
3093
3094
3095
3096
3097 void
3098 edit_move_display (WEdit *e, long line)
3099 {
3100 if (line < e->start_line)
3101 edit_scroll_upward (e, e->start_line - line);
3102 else
3103 edit_scroll_downward (e, line - e->start_line);
3104 }
3105
3106
3107
3108
3109 void
3110 edit_push_markers (WEdit *edit)
3111 {
3112 edit_push_undo_action (edit, MARK_1 + edit->mark1);
3113 edit_push_undo_action (edit, MARK_2 + edit->mark2);
3114 edit_push_undo_action (edit, MARK_CURS + edit->end_mark_curs);
3115 }
3116
3117
3118
3119 void
3120 edit_set_markers (WEdit *edit, off_t m1, off_t m2, long c1, long c2)
3121 {
3122 edit->mark1 = m1;
3123 edit->mark2 = m2;
3124 edit->column1 = c1;
3125 edit->column2 = c2;
3126 }
3127
3128
3129
3130
3131
3132
3133
3134
3135 gboolean
3136 eval_marks (WEdit *edit, off_t *start_mark, off_t *end_mark)
3137 {
3138 long end_mark_curs;
3139
3140 if (edit->mark1 == edit->mark2)
3141 {
3142 *start_mark = *end_mark = 0;
3143 edit->column2 = edit->column1 = 0;
3144 return FALSE;
3145 }
3146
3147 if (edit->end_mark_curs < 0)
3148 end_mark_curs = edit->buffer.curs1;
3149 else
3150 end_mark_curs = edit->end_mark_curs;
3151
3152 if (edit->mark2 >= 0)
3153 {
3154 *start_mark = MIN (edit->mark1, edit->mark2);
3155 *end_mark = MAX (edit->mark1, edit->mark2);
3156 }
3157 else
3158 {
3159 *start_mark = MIN (edit->mark1, end_mark_curs);
3160 *end_mark = MAX (edit->mark1, end_mark_curs);
3161 edit->column2 = edit->curs_col + edit->over_col;
3162 }
3163
3164 if (edit->column_highlight
3165 && ((edit->mark1 > end_mark_curs && edit->column1 < edit->column2)
3166 || (edit->mark1 < end_mark_curs && edit->column1 > edit->column2)))
3167 {
3168 off_t start_bol, start_eol;
3169 off_t end_bol, end_eol;
3170 long col1, col2;
3171 off_t diff1, diff2;
3172
3173 start_bol = edit_buffer_get_bol (&edit->buffer, *start_mark);
3174 start_eol = edit_buffer_get_eol (&edit->buffer, start_bol - 1) + 1;
3175 end_bol = edit_buffer_get_bol (&edit->buffer, *end_mark);
3176 end_eol = edit_buffer_get_eol (&edit->buffer, *end_mark);
3177 col1 = MIN (edit->column1, edit->column2);
3178 col2 = MAX (edit->column1, edit->column2);
3179
3180 diff1 = edit_move_forward3 (edit, start_bol, col2, 0) -
3181 edit_move_forward3 (edit, start_bol, col1, 0);
3182 diff2 = edit_move_forward3 (edit, end_bol, col2, 0) -
3183 edit_move_forward3 (edit, end_bol, col1, 0);
3184
3185 *start_mark -= diff1;
3186 *end_mark += diff2;
3187 *start_mark = MAX (*start_mark, start_eol);
3188 *end_mark = MIN (*end_mark, end_eol);
3189 }
3190
3191 return TRUE;
3192 }
3193
3194
3195
3196
3197 void
3198 edit_mark_cmd (WEdit *edit, gboolean unmark)
3199 {
3200 edit_push_markers (edit);
3201 if (unmark)
3202 {
3203 edit_set_markers (edit, 0, 0, 0, 0);
3204 edit->force |= REDRAW_PAGE;
3205 }
3206 else if (edit->mark2 >= 0)
3207 {
3208 edit->end_mark_curs = -1;
3209 edit_set_markers (edit, edit->buffer.curs1, -1, edit->curs_col + edit->over_col,
3210 edit->curs_col + edit->over_col);
3211 edit->force |= REDRAW_PAGE;
3212 }
3213 else
3214 {
3215 edit->end_mark_curs = edit->buffer.curs1;
3216 edit_set_markers (edit, edit->mark1, edit->buffer.curs1, edit->column1,
3217 edit->curs_col + edit->over_col);
3218 }
3219 }
3220
3221
3222
3223
3224 void
3225 edit_mark_current_word_cmd (WEdit *edit)
3226 {
3227 long pos;
3228
3229 for (pos = edit->buffer.curs1; pos != 0; pos--)
3230 {
3231 int c1, c2;
3232
3233 c1 = edit_buffer_get_byte (&edit->buffer, pos);
3234 c2 = edit_buffer_get_byte (&edit->buffer, pos - 1);
3235 if (!isspace (c1) && isspace (c2))
3236 break;
3237 if ((my_type_of (c1) & my_type_of (c2)) == 0)
3238 break;
3239 }
3240 edit->mark1 = pos;
3241
3242 for (; pos < edit->buffer.size; pos++)
3243 {
3244 int c1, c2;
3245
3246 c1 = edit_buffer_get_byte (&edit->buffer, pos);
3247 c2 = edit_buffer_get_byte (&edit->buffer, pos + 1);
3248 if (!isspace (c1) && isspace (c2))
3249 break;
3250 if ((my_type_of (c1) & my_type_of (c2)) == 0)
3251 break;
3252 }
3253 edit->mark2 = MIN (pos + 1, edit->buffer.size);
3254
3255 edit->force |= REDRAW_LINE_ABOVE | REDRAW_AFTER_CURSOR;
3256 }
3257
3258
3259
3260 void
3261 edit_mark_current_line_cmd (WEdit *edit)
3262 {
3263 edit->mark1 = edit_buffer_get_current_bol (&edit->buffer);
3264 edit->mark2 = edit_buffer_get_current_eol (&edit->buffer);
3265
3266 edit->force |= REDRAW_LINE_ABOVE | REDRAW_AFTER_CURSOR;
3267 }
3268
3269
3270
3271 void
3272 edit_delete_line (WEdit *edit)
3273 {
3274
3275
3276
3277
3278
3279 while (edit_buffer_get_current_byte (&edit->buffer) != '\n')
3280 (void) edit_delete (edit, TRUE);
3281
3282
3283
3284
3285
3286
3287 (void) edit_delete (edit, TRUE);
3288
3289
3290
3291
3292
3293 while (edit_buffer_get_previous_byte (&edit->buffer) != '\n')
3294 (void) edit_backspace (edit, TRUE);
3295 }
3296
3297
3298
3299 void
3300 edit_push_key_press (WEdit *edit)
3301 {
3302 edit_push_undo_action (edit, KEY_PRESS + edit->start_display);
3303 if (edit->mark2 == -1)
3304 {
3305 edit_push_undo_action (edit, MARK_1 + edit->mark1);
3306 edit_push_undo_action (edit, MARK_CURS + edit->end_mark_curs);
3307 }
3308 }
3309
3310
3311
3312 void
3313 edit_find_bracket (WEdit *edit)
3314 {
3315 edit->bracket = edit_get_bracket (edit, 1, 10000);
3316 if (edit->last_bracket != edit->bracket)
3317 edit->force |= REDRAW_PAGE;
3318 edit->last_bracket = edit->bracket;
3319 }
3320
3321
3322
3323
3324
3325
3326
3327
3328
3329
3330
3331
3332 void
3333 edit_execute_key_command (WEdit *edit, long command, int char_for_insertion)
3334 {
3335 if (command == CK_MacroStartRecord || command == CK_RepeatStartRecord
3336 || (macro_index < 0
3337 && (command == CK_MacroStartStopRecord || command == CK_RepeatStartStopRecord)))
3338 {
3339 macro_index = 0;
3340 edit->force |= REDRAW_CHAR_ONLY | REDRAW_LINE;
3341 return;
3342 }
3343 if (macro_index != -1)
3344 {
3345 edit->force |= REDRAW_COMPLETELY;
3346 if (command == CK_MacroStopRecord || command == CK_MacroStartStopRecord)
3347 {
3348 edit_store_macro_cmd (edit);
3349 macro_index = -1;
3350 return;
3351 }
3352 if (command == CK_RepeatStopRecord || command == CK_RepeatStartStopRecord)
3353 {
3354 edit_repeat_macro_cmd (edit);
3355 macro_index = -1;
3356 return;
3357 }
3358 }
3359
3360 if (macro_index >= 0 && macro_index < MAX_MACRO_LENGTH - 1)
3361 {
3362 record_macro_buf[macro_index].action = command;
3363 record_macro_buf[macro_index++].ch = char_for_insertion;
3364 }
3365
3366 if (command != CK_Undo && command != CK_ExtendedKeyMap)
3367 edit_push_key_press (edit);
3368
3369 edit_execute_cmd (edit, command, char_for_insertion);
3370 if (edit->column_highlight)
3371 edit->force |= REDRAW_PAGE;
3372 }
3373
3374
3375
3376
3377
3378
3379
3380
3381 void
3382 edit_execute_cmd (WEdit *edit, long command, int char_for_insertion)
3383 {
3384 WRect *w = &WIDGET (edit)->rect;
3385
3386 if (command == CK_WindowFullscreen)
3387 {
3388 edit_toggle_fullscreen (edit);
3389 return;
3390 }
3391
3392
3393 if (edit_handle_move_resize (edit, command))
3394 return;
3395
3396 edit->force |= REDRAW_LINE;
3397
3398
3399
3400 if (edit->found_len || edit->column_highlight)
3401 edit->force |= REDRAW_PAGE;
3402
3403 switch (command)
3404 {
3405
3406 case CK_MarkLeft:
3407 case CK_MarkRight:
3408 case CK_MarkToWordBegin:
3409 case CK_MarkToWordEnd:
3410 case CK_MarkToHome:
3411 case CK_MarkToEnd:
3412 case CK_MarkUp:
3413 case CK_MarkDown:
3414 case CK_MarkPageUp:
3415 case CK_MarkPageDown:
3416 case CK_MarkToFileBegin:
3417 case CK_MarkToFileEnd:
3418 case CK_MarkToPageBegin:
3419 case CK_MarkToPageEnd:
3420 case CK_MarkScrollUp:
3421 case CK_MarkScrollDown:
3422 case CK_MarkParagraphUp:
3423 case CK_MarkParagraphDown:
3424
3425 case CK_MarkColumnPageUp:
3426 case CK_MarkColumnPageDown:
3427 case CK_MarkColumnLeft:
3428 case CK_MarkColumnRight:
3429 case CK_MarkColumnUp:
3430 case CK_MarkColumnDown:
3431 case CK_MarkColumnScrollUp:
3432 case CK_MarkColumnScrollDown:
3433 case CK_MarkColumnParagraphUp:
3434 case CK_MarkColumnParagraphDown:
3435 edit->column_highlight = 0;
3436 if (edit->highlight == 0 || (edit->mark2 != -1 && edit->mark1 != edit->mark2))
3437 {
3438 edit_mark_cmd (edit, TRUE);
3439 edit_mark_cmd (edit, FALSE);
3440 }
3441 edit->highlight = 1;
3442 break;
3443
3444
3445 default:
3446 if (edit->highlight)
3447 edit_mark_cmd (edit, FALSE);
3448 edit->highlight = 0;
3449 }
3450
3451
3452 if (command == CK_Undo)
3453 {
3454 edit->redo_stack_reset = 0;
3455 edit_group_undo (edit);
3456 edit->found_len = 0;
3457 edit->prev_col = edit_get_col (edit);
3458 edit->search_start = edit->buffer.curs1;
3459 return;
3460 }
3461
3462 if (command == CK_Redo)
3463 {
3464 edit->redo_stack_reset = 0;
3465 edit_do_redo (edit);
3466 edit->found_len = 0;
3467 edit->prev_col = edit_get_col (edit);
3468 edit->search_start = edit->buffer.curs1;
3469 return;
3470 }
3471
3472 edit->redo_stack_reset = 1;
3473
3474
3475 if (char_for_insertion >= 0)
3476 {
3477
3478 if (!edit_options.persistent_selections && edit->mark1 != edit->mark2)
3479 edit_block_delete_cmd (edit);
3480
3481 if (edit->overwrite)
3482 {
3483
3484 #ifdef HAVE_CHARSET
3485 if (!mc_global.utf8_display || edit->charpoint == 0)
3486 #endif
3487 if (edit_buffer_get_current_byte (&edit->buffer) != '\n')
3488 edit_delete (edit, FALSE);
3489 }
3490 if (edit_options.cursor_beyond_eol && edit->over_col > 0)
3491 edit_insert_over (edit);
3492 #ifdef HAVE_CHARSET
3493
3494
3495
3496
3497 if (char_for_insertion > 127 && str_isutf8 (get_codepage_id (mc_global.source_codepage))
3498 && !mc_global.utf8_display)
3499 {
3500 unsigned char str[UTF8_CHAR_LEN + 1];
3501 size_t i;
3502 int res;
3503
3504 res = g_unichar_to_utf8 (char_for_insertion, (char *) str);
3505 if (res == 0)
3506 {
3507 str[0] = '.';
3508 str[1] = '\0';
3509 }
3510 else
3511 str[res] = '\0';
3512
3513 for (i = 0; i <= UTF8_CHAR_LEN && str[i] != '\0'; i++)
3514 {
3515 char_for_insertion = str[i];
3516 edit_insert (edit, char_for_insertion);
3517 }
3518 }
3519 else
3520 #endif
3521 edit_insert (edit, char_for_insertion);
3522
3523 if (edit_options.auto_para_formatting)
3524 {
3525 format_paragraph (edit, FALSE);
3526 edit->force |= REDRAW_PAGE;
3527 }
3528 else
3529 check_and_wrap_line (edit);
3530 edit->found_len = 0;
3531 edit->prev_col = edit_get_col (edit);
3532 edit->search_start = edit->buffer.curs1;
3533 edit_find_bracket (edit);
3534 return;
3535 }
3536
3537 switch (command)
3538 {
3539 case CK_TopOnScreen:
3540 case CK_BottomOnScreen:
3541 case CK_Top:
3542 case CK_Bottom:
3543 case CK_PageUp:
3544 case CK_PageDown:
3545 case CK_Home:
3546 case CK_End:
3547 case CK_Up:
3548 case CK_Down:
3549 case CK_Left:
3550 case CK_Right:
3551 case CK_WordLeft:
3552 case CK_WordRight:
3553 if (!edit_options.persistent_selections && edit->mark2 >= 0)
3554 {
3555 if (edit->column_highlight)
3556 edit_push_undo_action (edit, COLUMN_ON);
3557 edit->column_highlight = 0;
3558 edit_mark_cmd (edit, TRUE);
3559 }
3560 break;
3561 default:
3562 break;
3563 }
3564
3565 switch (command)
3566 {
3567 case CK_TopOnScreen:
3568 case CK_BottomOnScreen:
3569 case CK_MarkToPageBegin:
3570 case CK_MarkToPageEnd:
3571 case CK_Up:
3572 case CK_Down:
3573 case CK_WordLeft:
3574 case CK_WordRight:
3575 case CK_MarkToWordBegin:
3576 case CK_MarkToWordEnd:
3577 case CK_MarkUp:
3578 case CK_MarkDown:
3579 case CK_MarkColumnUp:
3580 case CK_MarkColumnDown:
3581 if (edit->mark2 == -1)
3582 break;
3583 MC_FALLTHROUGH;
3584 case CK_Left:
3585 case CK_Right:
3586 case CK_MarkLeft:
3587 case CK_MarkRight:
3588 edit->force |= REDRAW_CHAR_ONLY;
3589 break;
3590 default:
3591 break;
3592 }
3593
3594
3595 switch (command)
3596 {
3597 case CK_BackSpace:
3598
3599 if (!edit_options.persistent_selections && edit->mark1 != edit->mark2)
3600 edit_block_delete_cmd (edit);
3601 else if (edit_options.cursor_beyond_eol && edit->over_col > 0)
3602 edit->over_col--;
3603 else if (edit_options.backspace_through_tabs && is_in_indent (&edit->buffer))
3604 {
3605 while (edit_buffer_get_previous_byte (&edit->buffer) != '\n' && edit->buffer.curs1 > 0)
3606 edit_backspace (edit, TRUE);
3607 }
3608 else if (edit_options.fake_half_tabs && is_in_indent (&edit->buffer)
3609 && right_of_four_spaces (edit))
3610 {
3611 int i;
3612
3613 for (i = 0; i < HALF_TAB_SIZE; i++)
3614 edit_backspace (edit, TRUE);
3615 }
3616 else
3617 edit_backspace (edit, FALSE);
3618 break;
3619 case CK_Delete:
3620
3621 if (!edit_options.persistent_selections && edit->mark1 != edit->mark2)
3622 edit_block_delete_cmd (edit);
3623 else
3624 {
3625 if (edit_options.cursor_beyond_eol && edit->over_col > 0)
3626 edit_insert_over (edit);
3627
3628 if (edit_options.fake_half_tabs && is_in_indent (&edit->buffer)
3629 && left_of_four_spaces (edit))
3630 {
3631 int i;
3632
3633 for (i = 1; i <= HALF_TAB_SIZE; i++)
3634 edit_delete (edit, TRUE);
3635 }
3636 else
3637 edit_delete (edit, FALSE);
3638 }
3639 break;
3640 case CK_DeleteToWordBegin:
3641 edit->over_col = 0;
3642 edit_left_delete_word (edit);
3643 break;
3644 case CK_DeleteToWordEnd:
3645 if (edit_options.cursor_beyond_eol && edit->over_col > 0)
3646 edit_insert_over (edit);
3647
3648 edit_right_delete_word (edit);
3649 break;
3650 case CK_DeleteLine:
3651 edit_delete_line (edit);
3652 break;
3653 case CK_DeleteToHome:
3654 edit_delete_to_line_begin (edit);
3655 break;
3656 case CK_DeleteToEnd:
3657 edit_delete_to_line_end (edit);
3658 break;
3659 case CK_Enter:
3660 edit->over_col = 0;
3661 if (edit_options.auto_para_formatting)
3662 {
3663 edit_double_newline (edit);
3664 if (edit_options.return_does_auto_indent && !bracketed_pasting_in_progress)
3665 edit_auto_indent (edit);
3666 format_paragraph (edit, FALSE);
3667 }
3668 else
3669 {
3670 edit_insert (edit, '\n');
3671 if (edit_options.return_does_auto_indent && !bracketed_pasting_in_progress)
3672 edit_auto_indent (edit);
3673 }
3674 break;
3675 case CK_Return:
3676 edit_insert (edit, '\n');
3677 break;
3678
3679 case CK_MarkColumnPageUp:
3680 edit->column_highlight = 1;
3681 MC_FALLTHROUGH;
3682 case CK_PageUp:
3683 case CK_MarkPageUp:
3684 edit_move_up (edit, w->lines - (edit->fullscreen ? 1 : 2), TRUE);
3685 break;
3686 case CK_MarkColumnPageDown:
3687 edit->column_highlight = 1;
3688 MC_FALLTHROUGH;
3689 case CK_PageDown:
3690 case CK_MarkPageDown:
3691 edit_move_down (edit, w->lines - (edit->fullscreen ? 1 : 2), TRUE);
3692 break;
3693 case CK_MarkColumnLeft:
3694 edit->column_highlight = 1;
3695 MC_FALLTHROUGH;
3696 case CK_Left:
3697 case CK_MarkLeft:
3698 if (edit_options.fake_half_tabs && is_in_indent (&edit->buffer)
3699 && right_of_four_spaces (edit))
3700 {
3701 if (edit_options.cursor_beyond_eol && edit->over_col > 0)
3702 edit->over_col--;
3703 else
3704 edit_cursor_move (edit, -HALF_TAB_SIZE);
3705 edit->force &= (0xFFF - REDRAW_CHAR_ONLY);
3706 }
3707 else
3708 edit_left_char_move_cmd (edit);
3709 break;
3710 case CK_MarkColumnRight:
3711 edit->column_highlight = 1;
3712 MC_FALLTHROUGH;
3713 case CK_Right:
3714 case CK_MarkRight:
3715 if (edit_options.fake_half_tabs && is_in_indent (&edit->buffer)
3716 && left_of_four_spaces (edit))
3717 {
3718 edit_cursor_move (edit, HALF_TAB_SIZE);
3719 edit->force &= (0xFFF - REDRAW_CHAR_ONLY);
3720 }
3721 else
3722 edit_right_char_move_cmd (edit);
3723 break;
3724 case CK_TopOnScreen:
3725 case CK_MarkToPageBegin:
3726 edit_begin_page (edit);
3727 break;
3728 case CK_BottomOnScreen:
3729 case CK_MarkToPageEnd:
3730 edit_end_page (edit);
3731 break;
3732 case CK_WordLeft:
3733 case CK_MarkToWordBegin:
3734 edit->over_col = 0;
3735 edit_left_word_move_cmd (edit);
3736 break;
3737 case CK_WordRight:
3738 case CK_MarkToWordEnd:
3739 edit->over_col = 0;
3740 edit_right_word_move_cmd (edit);
3741 break;
3742 case CK_MarkColumnUp:
3743 edit->column_highlight = 1;
3744 MC_FALLTHROUGH;
3745 case CK_Up:
3746 case CK_MarkUp:
3747 edit_move_up (edit, 1, FALSE);
3748 break;
3749 case CK_MarkColumnDown:
3750 edit->column_highlight = 1;
3751 MC_FALLTHROUGH;
3752 case CK_Down:
3753 case CK_MarkDown:
3754 edit_move_down (edit, 1, FALSE);
3755 break;
3756 case CK_MarkColumnParagraphUp:
3757 edit->column_highlight = 1;
3758 MC_FALLTHROUGH;
3759 case CK_ParagraphUp:
3760 case CK_MarkParagraphUp:
3761 edit_move_up_paragraph (edit, FALSE);
3762 break;
3763 case CK_MarkColumnParagraphDown:
3764 edit->column_highlight = 1;
3765 MC_FALLTHROUGH;
3766 case CK_ParagraphDown:
3767 case CK_MarkParagraphDown:
3768 edit_move_down_paragraph (edit, FALSE);
3769 break;
3770 case CK_MarkColumnScrollUp:
3771 edit->column_highlight = 1;
3772 MC_FALLTHROUGH;
3773 case CK_ScrollUp:
3774 case CK_MarkScrollUp:
3775 edit_move_up (edit, 1, TRUE);
3776 break;
3777 case CK_MarkColumnScrollDown:
3778 edit->column_highlight = 1;
3779 MC_FALLTHROUGH;
3780 case CK_ScrollDown:
3781 case CK_MarkScrollDown:
3782 edit_move_down (edit, 1, TRUE);
3783 break;
3784 case CK_Home:
3785 case CK_MarkToHome:
3786 edit_cursor_to_bol (edit);
3787 break;
3788 case CK_End:
3789 case CK_MarkToEnd:
3790 edit_cursor_to_eol (edit);
3791 break;
3792 case CK_Tab:
3793
3794 if (edit->mark1 != edit->mark2 && !edit_options.persistent_selections)
3795 {
3796 if (edit->mark2 < 0)
3797 edit_mark_cmd (edit, FALSE);
3798 edit_move_block_to_right (edit);
3799 }
3800 else
3801 {
3802 if (edit_options.cursor_beyond_eol)
3803 edit_insert_over (edit);
3804 edit_tab_cmd (edit);
3805 if (edit_options.auto_para_formatting)
3806 {
3807 format_paragraph (edit, FALSE);
3808 edit->force |= REDRAW_PAGE;
3809 }
3810 else
3811 check_and_wrap_line (edit);
3812 }
3813 break;
3814
3815 case CK_InsertOverwrite:
3816 edit->overwrite = !edit->overwrite;
3817 break;
3818
3819 case CK_Mark:
3820 if (edit->mark2 >= 0)
3821 {
3822 if (edit->column_highlight)
3823 edit_push_undo_action (edit, COLUMN_ON);
3824 edit->column_highlight = 0;
3825 }
3826 edit_mark_cmd (edit, FALSE);
3827 break;
3828 case CK_MarkColumn:
3829 if (!edit->column_highlight)
3830 edit_push_undo_action (edit, COLUMN_OFF);
3831 edit->column_highlight = 1;
3832 edit_mark_cmd (edit, FALSE);
3833 break;
3834 case CK_MarkAll:
3835 edit_set_markers (edit, 0, edit->buffer.size, 0, 0);
3836 edit->force |= REDRAW_PAGE;
3837 break;
3838 case CK_Unmark:
3839 if (edit->column_highlight)
3840 edit_push_undo_action (edit, COLUMN_ON);
3841 edit->column_highlight = 0;
3842 edit_mark_cmd (edit, TRUE);
3843 break;
3844 case CK_MarkWord:
3845 if (edit->column_highlight)
3846 edit_push_undo_action (edit, COLUMN_ON);
3847 edit->column_highlight = 0;
3848 edit_mark_current_word_cmd (edit);
3849 break;
3850 case CK_MarkLine:
3851 if (edit->column_highlight)
3852 edit_push_undo_action (edit, COLUMN_ON);
3853 edit->column_highlight = 0;
3854 edit_mark_current_line_cmd (edit);
3855 break;
3856
3857 case CK_Bookmark:
3858 book_mark_clear (edit, edit->buffer.curs_line, BOOK_MARK_FOUND_COLOR);
3859 if (book_mark_query_color (edit, edit->buffer.curs_line, BOOK_MARK_COLOR))
3860 book_mark_clear (edit, edit->buffer.curs_line, BOOK_MARK_COLOR);
3861 else
3862 book_mark_insert (edit, edit->buffer.curs_line, BOOK_MARK_COLOR);
3863 break;
3864 case CK_BookmarkFlush:
3865 book_mark_flush (edit, BOOK_MARK_COLOR);
3866 book_mark_flush (edit, BOOK_MARK_FOUND_COLOR);
3867 edit->force |= REDRAW_PAGE;
3868 break;
3869 case CK_BookmarkNext:
3870 if (edit->book_mark != NULL)
3871 {
3872 edit_book_mark_t *p;
3873
3874 p = book_mark_find (edit, edit->buffer.curs_line);
3875 if (p->next != NULL)
3876 {
3877 p = p->next;
3878 if (p->line >= edit->start_line + w->lines || p->line < edit->start_line)
3879 edit_move_display (edit, p->line - w->lines / 2);
3880 edit_move_to_line (edit, p->line);
3881 }
3882 }
3883 break;
3884 case CK_BookmarkPrev:
3885 if (edit->book_mark != NULL)
3886 {
3887 edit_book_mark_t *p;
3888
3889 p = book_mark_find (edit, edit->buffer.curs_line);
3890 while (p->line == edit->buffer.curs_line)
3891 if (p->prev != NULL)
3892 p = p->prev;
3893 if (p->line >= 0)
3894 {
3895 if (p->line >= edit->start_line + w->lines || p->line < edit->start_line)
3896 edit_move_display (edit, p->line - w->lines / 2);
3897 edit_move_to_line (edit, p->line);
3898 }
3899 }
3900 break;
3901
3902 case CK_Top:
3903 case CK_MarkToFileBegin:
3904 edit_move_to_top (edit);
3905 break;
3906 case CK_Bottom:
3907 case CK_MarkToFileEnd:
3908 edit_move_to_bottom (edit);
3909 break;
3910
3911 case CK_Copy:
3912 if (edit_options.cursor_beyond_eol && edit->over_col > 0)
3913 edit_insert_over (edit);
3914 edit_block_copy_cmd (edit);
3915 break;
3916 case CK_Remove:
3917 edit_block_delete_cmd (edit);
3918 break;
3919 case CK_Move:
3920 edit_block_move_cmd (edit);
3921 break;
3922
3923 case CK_BlockShiftLeft:
3924 if (edit->mark1 != edit->mark2)
3925 edit_move_block_to_left (edit);
3926 break;
3927 case CK_BlockShiftRight:
3928 if (edit->mark1 != edit->mark2)
3929 edit_move_block_to_right (edit);
3930 break;
3931 case CK_Store:
3932 edit_copy_to_X_buf_cmd (edit);
3933 break;
3934 case CK_Cut:
3935 edit_cut_to_X_buf_cmd (edit);
3936 break;
3937 case CK_Paste:
3938
3939 if (!edit_options.persistent_selections && edit->mark1 != edit->mark2)
3940 edit_block_delete_cmd (edit);
3941 if (edit_options.cursor_beyond_eol && edit->over_col > 0)
3942 edit_insert_over (edit);
3943 edit_paste_from_X_buf_cmd (edit);
3944 if (!edit_options.persistent_selections && edit->mark2 >= 0)
3945 {
3946 if (edit->column_highlight)
3947 edit_push_undo_action (edit, COLUMN_ON);
3948 edit->column_highlight = 0;
3949 edit_mark_cmd (edit, TRUE);
3950 }
3951 break;
3952 case CK_History:
3953 edit_paste_from_history (edit);
3954 break;
3955
3956 case CK_SaveAs:
3957 edit_save_as_cmd (edit);
3958 break;
3959 case CK_Save:
3960 edit_save_confirm_cmd (edit);
3961 break;
3962 case CK_BlockSave:
3963 edit_save_block_cmd (edit);
3964 break;
3965 case CK_InsertFile:
3966 edit_insert_file_cmd (edit);
3967 break;
3968
3969 case CK_FilePrev:
3970 edit_load_back_cmd (edit);
3971 break;
3972 case CK_FileNext:
3973 edit_load_forward_cmd (edit);
3974 break;
3975
3976 case CK_SyntaxChoose:
3977 edit_syntax_dialog (edit);
3978 break;
3979
3980 case CK_Search:
3981 edit_search_cmd (edit, FALSE);
3982 break;
3983 case CK_SearchContinue:
3984 edit_search_cmd (edit, TRUE);
3985 break;
3986 case CK_Replace:
3987 edit_replace_cmd (edit, FALSE);
3988 break;
3989 case CK_ReplaceContinue:
3990 edit_replace_cmd (edit, TRUE);
3991 break;
3992 case CK_Complete:
3993
3994 if (edit->mark1 != edit->mark2 && !edit_options.persistent_selections)
3995 edit_move_block_to_left (edit);
3996 else
3997 edit_complete_word_cmd (edit);
3998 break;
3999 case CK_Find:
4000 edit_get_match_keyword_cmd (edit);
4001 break;
4002
4003 #ifdef HAVE_ASPELL
4004 case CK_SpellCheckCurrentWord:
4005 edit_suggest_current_word (edit);
4006 break;
4007 case CK_SpellCheck:
4008 edit_spellcheck_file (edit);
4009 break;
4010 case CK_SpellCheckSelectLang:
4011 edit_set_spell_lang ();
4012 break;
4013 #endif
4014
4015 case CK_Date:
4016 {
4017 char s[BUF_MEDIUM];
4018
4019 char time_format[] = "_c";
4020 time_format[0] = '%';
4021
4022 FMT_LOCALTIME_CURRENT (s, sizeof (s), time_format);
4023 edit_print_string (edit, s);
4024 edit->force |= REDRAW_PAGE;
4025 }
4026 break;
4027 case CK_Goto:
4028 edit_goto_cmd (edit);
4029 break;
4030 case CK_ParagraphFormat:
4031 format_paragraph (edit, TRUE);
4032 edit->force |= REDRAW_PAGE;
4033 break;
4034 case CK_MacroDelete:
4035 edit_delete_macro_cmd (edit);
4036 break;
4037 case CK_MatchBracket:
4038 edit_goto_matching_bracket (edit);
4039 break;
4040 case CK_UserMenu:
4041 edit_user_menu (edit, NULL, -1);
4042 break;
4043 case CK_Sort:
4044 edit_sort_cmd (edit);
4045 break;
4046 case CK_ExternalCommand:
4047 edit_ext_cmd (edit);
4048 break;
4049 case CK_EditMail:
4050 edit_mail_dialog (edit);
4051 break;
4052 #ifdef HAVE_CHARSET
4053 case CK_SelectCodepage:
4054 edit_select_codepage_cmd (edit);
4055 break;
4056 #endif
4057 case CK_InsertLiteral:
4058 edit_insert_literal_cmd (edit);
4059 break;
4060 case CK_MacroStartStopRecord:
4061 edit_begin_end_macro_cmd (edit);
4062 break;
4063 case CK_RepeatStartStopRecord:
4064 edit_begin_end_repeat_cmd (edit);
4065 break;
4066 case CK_ExtendedKeyMap:
4067 WIDGET (edit)->ext_mode = TRUE;
4068 break;
4069 default:
4070 break;
4071 }
4072
4073
4074 if ((command / CK_PipeBlock (0)) == 1)
4075 edit_block_process_cmd (edit, command - CK_PipeBlock (0));
4076
4077
4078 switch (command)
4079 {
4080 case CK_Search:
4081 case CK_SearchContinue:
4082 case CK_Replace:
4083 case CK_ReplaceContinue:
4084 case CK_Complete:
4085 edit->prev_col = edit_get_col (edit);
4086 break;
4087 case CK_Up:
4088 case CK_MarkUp:
4089 case CK_MarkColumnUp:
4090 case CK_Down:
4091 case CK_MarkDown:
4092 case CK_MarkColumnDown:
4093 case CK_PageUp:
4094 case CK_MarkPageUp:
4095 case CK_MarkColumnPageUp:
4096 case CK_PageDown:
4097 case CK_MarkPageDown:
4098 case CK_MarkColumnPageDown:
4099 case CK_Top:
4100 case CK_MarkToFileBegin:
4101 case CK_Bottom:
4102 case CK_MarkToFileEnd:
4103 case CK_ParagraphUp:
4104 case CK_MarkParagraphUp:
4105 case CK_MarkColumnParagraphUp:
4106 case CK_ParagraphDown:
4107 case CK_MarkParagraphDown:
4108 case CK_MarkColumnParagraphDown:
4109 case CK_ScrollUp:
4110 case CK_MarkScrollUp:
4111 case CK_MarkColumnScrollUp:
4112 case CK_ScrollDown:
4113 case CK_MarkScrollDown:
4114 case CK_MarkColumnScrollDown:
4115 edit->search_start = edit->buffer.curs1;
4116 edit->found_len = 0;
4117 break;
4118 default:
4119 edit->found_len = 0;
4120 edit->prev_col = edit_get_col (edit);
4121 edit->search_start = edit->buffer.curs1;
4122 }
4123 edit_find_bracket (edit);
4124
4125 if (edit_options.auto_para_formatting)
4126 {
4127 switch (command)
4128 {
4129 case CK_BackSpace:
4130 case CK_Delete:
4131 case CK_DeleteToWordBegin:
4132 case CK_DeleteToWordEnd:
4133 case CK_DeleteToHome:
4134 case CK_DeleteToEnd:
4135 format_paragraph (edit, FALSE);
4136 edit->force |= REDRAW_PAGE;
4137 break;
4138 default:
4139 break;
4140 }
4141 }
4142 }
4143
4144
4145
4146 void
4147 edit_stack_init (void)
4148 {
4149 for (edit_stack_iterator = 0; edit_stack_iterator < MAX_HISTORY_MOVETO; edit_stack_iterator++)
4150 edit_arg_init (&edit_history_moveto[edit_stack_iterator], NULL, -1);
4151
4152 edit_stack_iterator = 0;
4153 }
4154
4155
4156
4157 void
4158 edit_stack_free (void)
4159 {
4160 for (edit_stack_iterator = 0; edit_stack_iterator < MAX_HISTORY_MOVETO; edit_stack_iterator++)
4161 vfs_path_free (edit_history_moveto[edit_stack_iterator].file_vpath, TRUE);
4162 }
4163
4164
4165
4166
4167 void
4168 edit_move_up (WEdit *edit, long i, gboolean do_scroll)
4169 {
4170 edit_move_updown (edit, i, do_scroll, TRUE);
4171 }
4172
4173
4174
4175
4176 void
4177 edit_move_down (WEdit *edit, long i, gboolean do_scroll)
4178 {
4179 edit_move_updown (edit, i, do_scroll, FALSE);
4180 }
4181
4182
4183
4184
4185
4186
4187
4188
4189
4190
4191 edit_arg_t *
4192 edit_arg_vpath_new (vfs_path_t *file_vpath, long line_number)
4193 {
4194 edit_arg_t *arg;
4195
4196 arg = g_new (edit_arg_t, 1);
4197 arg->file_vpath = file_vpath;
4198 arg->line_number = line_number;
4199
4200 return arg;
4201 }
4202
4203
4204
4205
4206
4207
4208
4209
4210
4211
4212 edit_arg_t *
4213 edit_arg_new (const char *file_name, long line_number)
4214 {
4215 return edit_arg_vpath_new (vfs_path_from_str (file_name), line_number);
4216 }
4217
4218
4219
4220
4221
4222
4223
4224
4225
4226
4227 void
4228 edit_arg_init (edit_arg_t *arg, vfs_path_t *vpath, long line)
4229 {
4230 arg->file_vpath = (vfs_path_t *) vpath;
4231 arg->line_number = line;
4232 }
4233
4234
4235
4236
4237
4238
4239
4240
4241
4242
4243 void
4244 edit_arg_assign (edit_arg_t *arg, vfs_path_t *vpath, long line)
4245 {
4246 vfs_path_free (arg->file_vpath, TRUE);
4247 edit_arg_init (arg, vpath, line);
4248 }
4249
4250
4251
4252
4253
4254
4255
4256
4257 void
4258 edit_arg_free (edit_arg_t *arg)
4259 {
4260 vfs_path_free (arg->file_vpath, TRUE);
4261 g_free (arg);
4262 }
4263
4264
4265
4266 const char *
4267 edit_get_file_name (const WEdit *edit)
4268 {
4269 return vfs_path_as_str (edit->filename_vpath);
4270 }
4271
4272