working on undo

This commit is contained in:
2025-11-29 13:05:12 -08:00
parent c47287e96e
commit 3b401e770e
3 changed files with 83 additions and 12 deletions

17
abuf.c
View File

@@ -74,6 +74,11 @@ ab_append(abuf *buf, const char *s, size_t len)
void void
ab_append_ab(abuf *buf, const abuf *other) ab_append_ab(abuf *buf, const abuf *other)
{ {
assert(buf != NULL);
if (other == NULL) {
return;
}
ab_append(buf, other->b, other->size); ab_append(buf, other->b, other->size);
} }
@@ -104,6 +109,18 @@ ab_prepend(abuf *buf, const char *s, const size_t len)
} }
void
ab_prepend_ab(abuf *buf, const abuf *other)
{
assert(buf != NULL);
if (other == NULL) {
return;
}
ab_prepend(buf, other->b, other->size);
}
void void
ab_free(abuf *buf) ab_free(abuf *buf)
{ {

66
undo.c
View File

@@ -1,6 +1,7 @@
#include <assert.h> #include <assert.h>
#include <stdlib.h> #include <stdlib.h>
#include "abuf.h" #include "abuf.h"
#include "buffer.h"
#include "undo.h" #include "undo.h"
@@ -18,7 +19,7 @@ undo_node_new(undo_kind kind)
ab_init(&node->text); ab_init(&node->text);
node->next = NULL; node->next = NULL;
node->parent = NULL; node->next = NULL;
return node; return node;
} }
@@ -101,7 +102,7 @@ undo_prepend(undo_tree *tree, abuf *buf)
assert(tree != NULL); assert(tree != NULL);
assert(tree->pending != NULL); assert(tree->pending != NULL);
ab_prepend_ab(tree->pending->text, buf); ab_prepend_ab(&tree->pending->text, buf);
} }
@@ -111,7 +112,7 @@ undo_append(undo_tree *tree, abuf *buf)
assert(tree != NULL); assert(tree != NULL);
assert(tree->pending != NULL); assert(tree->pending != NULL);
ab_append_ab(tree->pending->text, buf); ab_append_ab(&tree->pending->text, buf);
} }
@@ -121,7 +122,7 @@ undo_prependch(undo_tree *tree, char c)
assert(tree != NULL); assert(tree != NULL);
assert(tree->pending != NULL); assert(tree->pending != NULL);
ab_prependch(tree->pending->text, c); ab_prependch(&tree->pending->text, c);
} }
@@ -131,7 +132,7 @@ undo_appendch(undo_tree *tree, char c)
assert(tree != NULL); assert(tree != NULL);
assert(tree->pending != NULL); assert(tree->pending != NULL);
ab_appendch(tree->pending->text, c); ab_appendch(&tree->pending->text, c);
} }
@@ -144,10 +145,59 @@ undo_commit(undo_tree *tree)
return; return;
} }
if (tree->root == NULL) {
assert(tree->current == NULL);
tree->root = tree->pending;
tree->current = tree->pending;
tree->pending = NULL;
return;
}
assert(tree->current != NULL);
if (tree->current->next != NULL) {
undo_node_free_all(tree->current->next);
}
tree->pending->prev = tree->current;
tree->current->next = tree->pending;
tree->current = tree->pending;
tree->pending = NULL;
}
int
undo_apply(struct buffer *buf, int direction)
{
(void)buf;
(void)direction;
return 0;
}
int
editor_undo(struct buffer *buf)
{
if (buf == NULL) {
return 0;
}
undo_commit(&buf->tree);
return undo_apply(buf, UNDO_DIR_UNDO);
} }
void undo_apply(struct buffer *buf); int
void editor_undo(struct buffer *buf); editor_redo(struct buffer *buf)
void editor_redo(struct buffer *buf); {
if (buf == NULL) {
return 0;
}
undo_commit(&buf->tree);
return undo_apply(buf, UNDO_DIR_REDO);
}

12
undo.h
View File

@@ -10,6 +10,10 @@
struct buffer; struct buffer;
#define UNDO_DIR_UNDO -1
#define UNDO_DIR_REDO 1
typedef enum undo_kind { typedef enum undo_kind {
UNDO_INSERT = 1 << 0, UNDO_INSERT = 1 << 0,
UNDO_UNKNOWN = 1 << 1, UNDO_UNKNOWN = 1 << 1,
@@ -22,7 +26,7 @@ typedef struct undo_node {
abuf text; abuf text;
struct undo_node *next; struct undo_node *next;
struct undo_node *parent; struct undo_node *prev;
} undo_node; } undo_node;
@@ -44,9 +48,9 @@ void undo_append(undo_tree *tree, abuf *buf);
void undo_prependch(undo_tree *tree, char c); void undo_prependch(undo_tree *tree, char c);
void undo_appendch(undo_tree *tree, char c); void undo_appendch(undo_tree *tree, char c);
void undo_commit(undo_tree *tree); void undo_commit(undo_tree *tree);
void undo_apply(struct buffer *buf); int undo_apply(struct buffer *buf, int direction);
void editor_undo(struct buffer *buf); int editor_undo(struct buffer *buf);
void editor_redo(struct buffer *buf); int editor_redo(struct buffer *buf);
#endif #endif