commit 319166fdb8635a153c2c842426f97f69ea9af51c
parent 75577de0f5b81b5225c671403b12ea690a830346
Author: Byron Torres <b@torresjrjr.com>
Date: Mon, 20 Feb 2023 00:57:42 +0000
add cmd_append(), cmd_change(), cmd_insert()
Diffstat:
M | command.ha | | | 64 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++--- |
M | main.ha | | | 10 | ++++++++-- |
M | parse.ha | | | 8 | +++++++- |
3 files changed, 76 insertions(+), 6 deletions(-)
diff --git a/command.ha b/command.ha
@@ -177,9 +177,50 @@ fn assert_nonzero(s: *session, n: size) (void | invalidaddress) = {
};
};
-fn cmd_append(s: *session, cmd: *command) (void | error) = void;
+fn cmd_append(s: *session, cmd: *command) (void | error) = {
+ const n = get_linenum(cmd.linenums, s.buf.cursor);
+
+ for (let i = 0z; i < len(cmd.input); i += 1) {
+ const l = alloc(line { text = cmd.input[i], ... });
+ debug("cmd_append(): l.text={}", l.text);
+ buf_insert(&s.buf, n + 1 + i, l);
+ };
+
+ s.buf.cursor = n + len(cmd.input);
+};
+
+fn cmd_change(s: *session, cmd: *command) (void | error) = {
+ const (a, b) = get_range(
+ s,
+ &cmd.linenums,
+ s.buf.cursor,
+ s.buf.cursor,
+ )?;
+ if (a == 0) {
+ a = 1;
+ if (b == 0) {
+ b = 1;
+ };
+ };
+
+ buf_delete(&s.buf, a, b);
-fn cmd_change(s: *session, cmd: *command) (void | error) = void;
+ for (let i = 0z; i < len(cmd.input); i += 1) {
+ const l = alloc(line { text = cmd.input[i], ... });
+ debug("cmd_append(): l.text={}", l.text);
+ buf_insert(&s.buf, a + i, l);
+ };
+
+ s.buf.cursor = if (len(cmd.input) == 0) {
+ yield if (len(s.buf.lines) == a) {
+ yield a - 1;
+ } else {
+ yield a;
+ };
+ } else {
+ yield a + len(cmd.input) - 1;
+ };
+};
fn cmd_delete(s: *session, cmd: *command) (void | error) = {
const (a, b) = get_range(
@@ -265,7 +306,24 @@ fn cmd_helpmode(s: *session, cmd: *command) (void | error) = {
};
};
-fn cmd_insert(s: *session, cmd: *command) (void | error) = void;
+fn cmd_insert(s: *session, cmd: *command) (void | error) = {
+ const n = get_linenum(cmd.linenums, s.buf.cursor);
+ if (n == 0) {
+ n = 1;
+ };
+
+ for (let i = 0z; i < len(cmd.input); i += 1) {
+ const l = alloc(line { text = cmd.input[i], ... });
+ debug("cmd_append(): l.text={}", l.text);
+ buf_insert(&s.buf, n + i, l);
+ };
+
+ s.buf.cursor = if (len(cmd.input) == 0) {
+ yield n;
+ } else {
+ yield n + len(cmd.input) - 1;
+ };
+};
fn cmd_join(s: *session, cmd: *command) (void | error) = {
const (a, b) = get_range(
diff --git a/main.ha b/main.ha
@@ -82,7 +82,7 @@ export fn main() void = {
let cmd = command { ... };
for (true) :repl {
- if (s.promptmode) {
+ if (s.promptmode && s.mode == mode::COMMAND) {
fmt::error(s.prompt)!;
};
@@ -117,13 +117,19 @@ export fn main() void = {
// TODO: handle all ": void"s
execute(&s, &cmd): void;
//cmd = command { ... };
+ } else {
+ s.mode = mode::INPUT;
+ continue;
};
case mode::INPUT =>
if (input == ".") {
+ execute(&s, &cmd): void;
+ delete(cmd.input[..]);
s.mode = mode::COMMAND;
continue;
};
- append(cmd.input, input);
+ debug("repl: input={}", input);
+ append(cmd.input, strings::dup(input));
};
};
diff --git a/parse.ha b/parse.ha
@@ -75,11 +75,17 @@ fn parse(cmd: *command, input: str) (bool | parseerror) = {
return true;
// .[s] where 's' is '(l|n|p)'
- case 'a', 'c', 'd', 'h', 'H', 'i', 'j', 'l', 'n', 'p', 'P', 'u', '=' =>
+ case 'd', 'h', 'H', 'j', 'l', 'n', 'p', 'P', 'u', '=' =>
cmd.printmode = scan_suffix(&iter);
scan_end_assert(&iter)?;
return true;
+ // .[s]
+ case 'a', 'c', 'i' =>
+ cmd.printmode = scan_suffix(&iter);
+ scan_end_assert(&iter)?;
+ return false;
+
// .[s][ ]<addr>
case 'm', 't' =>
cmd.printmode = scan_suffix(&iter);