~torresjrjr/public-inbox

ed: hist: reset cursor following POSIX v2 REJECTED

Curtis Arthaud: 1
 hist: reset cursor following POSIX

 3 files changed, 32 insertions(+), 17 deletions(-)
Export patchset (mbox)
How do I use this?

Copy & paste the following snippet into your terminal to import this patchset into git:

curl -s https://lists.sr.ht/~torresjrjr/public-inbox/patches/50403/mbox | git am -3
Learn more about email & git

[PATCH ed v2] hist: reset cursor following POSIX Export this patch

Signed-off-by: Curtis Arthaud <uku82@gmx.fr>
---
I incorporated the idea I mentioned earlier.
Seems to fix things nicely?

 buffer.ha  |  6 +++---
 command.ha |  3 +++
 history.ha | 40 ++++++++++++++++++++++++++--------------
 3 files changed, 32 insertions(+), 17 deletions(-)

diff --git a/buffer.ha b/buffer.ha
index a32216f..c0b40c6 100644
--- a/buffer.ha
@@ -35,7 +35,7 @@ fn buf_insert(buf: *Buffer, n: size, ls: *Line...) void = {

	buf.modified = true;

	hist_append(buf, (n, len(ls)): Addition);
	hist_append(buf, (n, len(ls), buf.cursor): Addition);

//	debug("buf_insert(): len('last changeseq')={}", len(buf.hist[len(buf.hist) - 1]));
};
@@ -56,7 +56,7 @@ fn buf_delete(buf: *Buffer, a: size, b: size) void = {

	buf.modified = true;

	hist_append(buf, (a, (b + 1 - a)): Deletion);
	hist_append(buf, (a, (b + 1 - a), buf.cursor): Deletion);

//	debug("buf_delete(): len('last changeseq')={}", len(buf.hist[len(buf.hist) - 1]));
};
@@ -85,7 +85,7 @@ fn buf_read(

	insert(buf.lines[n + 1], lines...);

	hist_append(buf, (n + 1, m): Addition);
	hist_append(buf, (n + 1, m, buf.cursor): Addition);

	buf.modified = true;

diff --git a/command.ha b/command.ha
index 62d24ef..cf65730 100644
--- a/command.ha
+++ b/command.ha
@@ -616,11 +616,14 @@ fn cmd_undo(s: *Session, cmd: *Command) (void | Error) = {

	switch (s.undomode) {
	case UndoMode::POSIX =>
		const cur = s.buf.cursor;
		if (s.buf.redolastchange) {
			hist_redo(s.buf)?;
			hist_reset_undo_cursor(s.buf, cur);
			s.buf.redolastchange = false;
		} else {
			hist_undo(s.buf)?;
			hist_reset_undo_cursor(s.buf, cur);
			s.buf.redolastchange = true;
		};
	case UndoMode::FULL =>
diff --git a/history.ha b/history.ha
index ea109a2..bacae82 100644
--- a/history.ha
+++ b/history.ha
@@ -7,11 +7,11 @@ type ChangeSeq = []Change;
// A record of a single arbitrary buffer change.
type Change = (Addition | Deletion);

// The addition of a buffer chunk (start position, chunk size).
type Addition = (size, size);
// The addition of a buffer chunk (start position, chunk size, cursor).
type Addition = (size, size, size);

// The deletion of a buffer chunk (start position, chunk size).
type Deletion = (size, size);
// The deletion of a buffer chunk (start position, chunk size, cursor).
type Deletion = (size, size, size);

// The effect of the undo command.
type UndoMode = enum{
@@ -60,19 +60,18 @@ fn hist_undo(buf: *Buffer) (void | NoHistory) = {
	for (let j = len(seq) - 1; j < len(seq); j -= 1)
		match (seq[j]) {
		case let deln: Deletion =>
			let (n, m) = deln;
			let (n, m, cur) = deln;
			let lentrash = len(buf.trash);
			let lines = buf.trash[(lentrash - m)..];
			insert(buf.lines[n], lines...);
			delete(buf.trash[(lentrash - m)..]);
			buf.cursor = (n + m) - 1;
			buf.cursor = cur;
		case let addn: Addition =>
			let (n, m) = addn;
			let (n, m, cur) = addn;
			let lines = buf.lines[n..(n + m)];
			insert(buf.trash[0], lines...);
			delete(buf.lines[n..(n + m)]);
			let prev = addr_prevline(buf, n);
			buf.cursor = prev;
			buf.cursor = cur;
		};
};

@@ -86,20 +85,33 @@ fn hist_redo(buf: *Buffer) (void | NoHistory) = {
	for (let i = 0z; i < len(seq); i += 1)
		match (seq[i]) {
		case let addn: Addition =>
			let (n, m) = addn;
			let (n, m, cur) = addn;
			//let lentrash = len(buf.trash);
			//let lines = buf.trash[(lentrash - m)..];
			let lines = buf.trash[..m];
			insert(buf.lines[n], lines...);
			//delete(buf.trash[(lentrash - m)..]);
			delete(buf.trash[..m]);
			buf.cursor = (n + m) - 1;
			buf.cursor = cur;
		case let deln: Deletion =>
			let (n, m) = deln;
			let (n, m, cur) = deln;
			let lines = buf.lines[n..(n + m)];
			append(buf.trash, lines...);
			delete(buf.lines[n..(n + m)]);
			let prev = addr_prevline(buf, n);
			buf.cursor = prev;
			buf.cursor = cur;
		};
};

fn hist_reset_undo_cursor(buf: *Buffer, cur: size) void = {
	const seq = buf.hist[ len(buf.hist) - 1 ];
	hist_newseq(buf);
	for (let i = 0z; i < len(seq); i += 1)
		match (seq[i]) {
		case let addn: Addition =>
			let (n, m, c) = addn;
			hist_append(buf, (n, m, cur): Addition);
		case let deln: Deletion =>
			let (n, m, c) = deln;
			hist_append(buf, (n, m, cur): Deletion);
		};
};
--
2.44.0
I'm thinking something like:

	type Change = (Addition | Deletion | CursorMove);

	type CursorMove = (size, size); // (before, after)

	fn buf_updatecursor(buf: *Buffer, cur: size) void = {
		hist_append(buf, (buf.cursor, cur): CursorMove)
	};

	s/s.buf.cursor =/buf_updatecursor(/ # where appropriate

Though these changes would require some thought.