From 202146be752af88d7812dd3804e5234e692256ce Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marc=20Andr=C3=A9=20Tanner?= Date: Sun, 7 Feb 2016 13:19:18 +0100 Subject: vis: implement number increment and decrement functionality The default key bindings are not changed for now, because conflicts with multiple cursor alignment. --- main.c | 59 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 59 insertions(+) (limited to 'main.c') diff --git a/main.c b/main.c index 918f4c8..c3ae7a3 100644 --- a/main.c +++ b/main.c @@ -109,6 +109,8 @@ static const char *window(Vis*, const char *keys, const Arg *arg); static const char *unicode_info(Vis*, const char *keys, const Arg *arg); /* either go to count % of ile or to matching item */ static const char *percent(Vis*, const char *keys, const Arg *arg); +/* either increment (arg->i > 0) or decrement (arg->i < 0) number under cursor */ +static const char *number_increment_decrement(Vis*, const char *keys, const Arg *arg); enum { VIS_ACTION_EDITOR_SUSPEND, @@ -268,6 +270,8 @@ enum { VIS_ACTION_MOTION_CHARWISE, VIS_ACTION_MOTION_LINEWISE, VIS_ACTION_UNICODE_INFO, + VIS_ACTION_NUMBER_INCREMENT, + VIS_ACTION_NUMBER_DECREMENT, VIS_ACTION_NOP, }; @@ -1057,6 +1061,16 @@ static KeyAction vis_action[] = { "Show Unicode codepoint(s) of character under cursor", unicode_info, }, + [VIS_ACTION_NUMBER_INCREMENT] = { + "number-increment", + "Increment number under cursor", + number_increment_decrement, { .i = +1 } + }, + [VIS_ACTION_NUMBER_DECREMENT] = { + "number-decrement", + "Decrement number under cursor", + number_increment_decrement, { .i = -1 } + }, [VIS_ACTION_NOP] = { "nop", "Ignore key, do nothing", @@ -1618,6 +1632,51 @@ static const char *percent(Vis *vis, const char *keys, const Arg *arg) { return keys; } +static const char *number_increment_decrement(Vis *vis, const char *keys, const Arg *arg) { + View *view = vis_view(vis); + Text *txt = vis_text(vis); + + int delta = arg->i; + int count = vis_count_get(vis); + if (count != 0 && count != VIS_COUNT_UNKNOWN) + delta *= count; + + for (Cursor *c = view_cursors(view); c; c = view_cursors_next(c)) { + Filerange r = text_object_number(txt, view_cursors_pos(c)); + if (!text_range_valid(&r)) + continue; + char *buf = text_bytes_alloc0(txt, r.start, text_range_size(&r)); + if (buf) { + char *number = buf, fmt[255]; + if (number[0] == '-') + number++; + bool octal = number[0] == '0' && ('0' <= number[1] && number[1] <= '7'); + bool hex = number[0] == '0' && (number[1] == 'x' || number[1] == 'X'); + bool dec = !hex && !octal; + + long long value = strtoll(buf, NULL, 0); + value += delta; + if (dec) { + snprintf(fmt, sizeof fmt, "%lld", value); + } else if (hex) { + size_t len = strlen(number) - 2; + snprintf(fmt, sizeof fmt, "0x%0*llx", len, value); + } else { + size_t len = strlen(number) - 1; + snprintf(fmt, sizeof fmt, "0%0*llo", len, value); + } + text_delete_range(txt, &r); + text_insert(txt, r.start, fmt, strlen(fmt)); + view_cursors_to(c, r.start); + } + free(buf); + } + + vis_cancel(vis); + + return keys; +} + static Vis *vis; static void signal_handler(int signum, siginfo_t *siginfo, void *context) { -- cgit v1.2.3