ledit

Text editor (WIP)
git clone git://lumidify.org/ledit.git (fast, but not encrypted)
git clone https://lumidify.org/git/ledit.git (encrypted, but very slow)
Log | Files | Refs | README | LICENSE

commit e822581bc43838987d8830b54c5e2103056a1b18
parent 8c56c0d034a6e99583be2d9926946997c8fa82bb
Author: lumidify <nobody@lumidify.org>
Date:   Thu, 23 Dec 2021 21:06:42 +0100

Fix a few bugs

Diffstat:
MREADME | 2++
Mbuffer.h | 2+-
Mkeys_basic.c | 27++++++++++++++++++++-------
Mledit.1 | 3+++
Mview.c | 7++++---
5 files changed, 30 insertions(+), 11 deletions(-)

diff --git a/README b/README @@ -5,6 +5,8 @@ ledit is a vi-like text editor for people who switch between keyboard layouts frequently and/or work with languages that require complex text layout. +REQUIREMENTS: pango, xlib (extensions: xkb, xdbe) + The documentation can be viewed in ledit.1 or at the following locations: gopher://lumidify.org/0/doc/ledit/ledit-current.txt diff --git a/buffer.h b/buffer.h @@ -32,7 +32,7 @@ typedef struct { ledit_buffer_mark *marks; } ledit_buffer_marklist; -/* TODO: advisory lock on file? also check if modification date changed before writing */ +/* TODO: advisory lock on file */ struct ledit_buffer { ledit_common *common; /* common stuff, e.g. display, etc. */ char *filename; /* last opened filename */ diff --git a/keys_basic.c b/keys_basic.c @@ -9,6 +9,8 @@ and being deleted at some later time even though they're not shown anymore */ /* FIXME: delete everything concerned with selections in insert mode since they are now not allowed at all */ +/* FIXME: a lot of error checking in the individual functions may be redundant + now that more checking is done beforehand for the allowed keys */ #include <stdio.h> #include <stdlib.h> @@ -479,6 +481,7 @@ delete_selection(ledit_view *view) { return 0; } +/* FIXME: should these delete characters or graphemes? */ static struct action delete_chars_forwards(ledit_view *view, char *text, size_t len) { (void)text; @@ -936,7 +939,7 @@ change(ledit_view *view, char *text, size_t len) { return err_invalid_key(view); } else { struct key_stack_elem *e = push_key_stack(); - e->key = KEY_MOTIONALLOWED; + e->key = KEY_MOTIONALLOWED|KEY_NUMBERALLOWED; e->count = num; e->motion_cb = &change_cb; } @@ -999,9 +1002,11 @@ yank(ledit_view *view, char *text, size_t len) { } else { motion_callback cb = NULL; int num = get_key_repeat_and_motion_cb(view, &cb); - if (num == 0) - num = 1; + if (num == -1) + return err_invalid_key(view); if (cb == &yank_cb) { + if (num == 0) + num = 1; size_t new_line; int new_softline; get_new_line_softline( @@ -1014,10 +1019,11 @@ yank(ledit_view *view, char *text, size_t len) { clear_key_stack(); } else if (cb == NULL) { struct key_stack_elem *e = push_key_stack(); - e->key = KEY_MOTIONALLOWED; + e->key = KEY_MOTIONALLOWED|KEY_NUMBERALLOWED; e->count = num; e->motion_cb = &yank_cb; } else { + /* FIXME: proper error */ clear_key_stack(); } } @@ -1120,7 +1126,7 @@ delete(ledit_view *view, char *text, size_t len) { return err_invalid_key(view); } else { struct key_stack_elem *e = push_key_stack(); - e->key = KEY_MOTIONALLOWED; + e->key = KEY_MOTIONALLOWED|KEY_NUMBERALLOWED; e->count = num; e->motion_cb = &delete_cb; } @@ -1561,6 +1567,7 @@ move_cursor_left_right(ledit_view *view, int dir, int allow_illegal_index) { } else if (view->mode == NORMAL) { view_set_line_cursor_attrs(view, view->cur_line, view->cur_index); } + view->redraw = 1; discard_repetition_stack(); } clear_key_stack(); @@ -1683,6 +1690,7 @@ move_cursor_up_down(ledit_view *view, int dir) { } else if (view->mode == NORMAL) { view_set_line_cursor_attrs(view, view->cur_line, view->cur_index); } + view->redraw = 1; discard_repetition_stack(); } clear_key_stack(); @@ -1951,6 +1959,7 @@ jump_to_mark(ledit_view *view, char *text, size_t len) { (void)text; (void)len; grab_char_cb = &jump_to_mark_cb; + /* FIXME: should it be discarded here? */ discard_repetition_stack(); return (struct action){ACTION_NONE, NULL}; } @@ -2061,7 +2070,7 @@ search_str_backwards(char *haystack, size_t hlen, char *needle, size_t nlen, siz size_t new_index = start_index; for (; new_index > 0; new_index--) { if (!strncmp(haystack + new_index - 1, needle, nlen)) { - *ret = new_index; + *ret = new_index - 1; return 0; } } @@ -2189,6 +2198,7 @@ replace_cb(ledit_view *view, char *text, size_t len) { CHECK_VIEW_LOCKED(view); size_t start_index = view->cur_index; /* FIXME: replace with (key repeat) * text instead of just text */ + /* FIXME: cursor pos or char? */ size_t end_index = view_next_cursor_pos( view, view->cur_line, view->cur_index, 1 ); @@ -2339,7 +2349,10 @@ basic_key_handler(ledit_view *view, XEvent *event, int lang_index) { if (found && (type & KEY_ENSURE_CURSOR_SHOWN)) view_ensure_cursor_shown(view); - if (!found && n > 0) + if (!found && n > 0) { window_show_message(view->window, "Invalid key", -1); + discard_repetition_stack(); + clear_key_stack(); + } return act; } diff --git a/ledit.1 b/ledit.1 @@ -3,6 +3,9 @@ .\" bigword, etc. .\" commands - no good way for mapping found .\" difference between unicode char and grapheme +.\" x, X currently delete graphemes +.\" everything assumed to be utf8 +.\" marks sometimes char, sometimes line based .\" .\" WARNING: Some parts of this are stolen shamelessly from OpenBSD's .\" vi(1) manpage! diff --git a/view.c b/view.c @@ -1191,7 +1191,7 @@ view_delete_range_base( size_t new_line = 0, new_byte = 0; ledit_assert(line_index1 < view->lines_num); ledit_assert(line_index2 < view->lines_num); - ledit_range cur_range = {0, 0, 0, 0}; + ledit_range cur_range = {view->cur_line, view->cur_index, 0, 0}; /* FIXME: could this be simplified by just calculating the range and then using the non-line-based version? */ if (delmode == DELETE_HARDLINE) { @@ -1443,8 +1443,9 @@ view_delete_range_base( rgl1, rgb1, rgl2, rgb2, text_ret ); } - cur_range.line1 = view->cur_line; - cur_range.byte1 = view->cur_index; + /* note: line1/byte1 need to be set at the top since deleting text + might change the current line/byte of the view through the notify + functions */ cur_range.line2 = new_line; cur_range.byte2 = new_byte; undo_change_last_cur_range(view->buffer->undo, cur_range);