aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorRobin Haberkorn <robin.haberkorn@googlemail.com>2025-03-08 04:54:10 +0300
committerRobin Haberkorn <robin.haberkorn@googlemail.com>2025-03-08 05:11:56 +0300
commit7bcd3d8fee485d2fdd6af2d0362d2a59b374c724 (patch)
tree5bfecbc426a1adb976d2c13779709becffe7d016
parent4fc266d9ed6cbdc02021caa6f3b5edfb6025b0bf (diff)
downloadsciteco-7bcd3d8fee485d2fdd6af2d0362d2a59b374c724.tar.gz
fixed the `Y` command: no longer delete any characters after dot
* This has __always__ been broken. It's been especially annoying when pressing `Y` at the end of a line with trailing whitespace since the linebreak would also be deleted. This was because `Y` always deleted the entire word or non-word character-span. This was inconsistent with `V`. * We now use SCI_WORDSTART|ENDPOSITION instead of the keyboard commands. It therefore also requires less Scintilla messages (4+2*n vs. 4+4*n). Most importantly, we can now check for errors before changing the buffer, so there is no need to undo anything in case of errors. This should always be the preferred strategy. * Added test case.
-rw-r--r--src/core-commands.c54
-rw-r--r--tests/testsuite.at5
2 files changed, 28 insertions, 31 deletions
diff --git a/src/core-commands.c b/src/core-commands.c
index 0d23adb..06a451a 100644
--- a/src/core-commands.c
+++ b/src/core-commands.c
@@ -758,50 +758,42 @@ teco_state_start_word(teco_machine_main_t *ctx, GError **error)
}
}
+/*
+ * FIXME: would be nice to do this with constant amount of
+ * editor messages. E.g. by using custom algorithm accessing
+ * the internal document buffer.
+ */
static teco_bool_t
teco_delete_words(teco_int_t n)
{
- sptr_t pos, size;
-
if (!n)
return TECO_SUCCESS;
- pos = teco_interface_ssm(SCI_GETCURRENTPOS, 0, 0);
- size = teco_interface_ssm(SCI_GETLENGTH, 0, 0);
- teco_interface_ssm(SCI_BEGINUNDOACTION, 0, 0);
- /*
- * FIXME: would be nice to do this with constant amount of
- * editor messages. E.g. by using custom algorithm accessing
- * the internal document buffer.
- */
+ sptr_t pos, start_pos, end_pos;
+ pos = start_pos = end_pos = teco_interface_ssm(SCI_GETCURRENTPOS, 0, 0);
+
if (n > 0) {
while (n--) {
- sptr_t size = teco_interface_ssm(SCI_GETLENGTH, 0, 0);
- teco_interface_ssm(SCI_DELWORDRIGHTEND, 0, 0);
- if (size == teco_interface_ssm(SCI_GETLENGTH, 0, 0))
- break;
+ sptr_t old_pos = end_pos;
+ end_pos = teco_interface_ssm(SCI_WORDENDPOSITION, end_pos, FALSE);
+ end_pos = teco_interface_ssm(SCI_WORDENDPOSITION, end_pos, TRUE);
+ if (end_pos == old_pos)
+ return TECO_FAILURE;
}
} else {
- n *= -1;
- while (n--) {
- sptr_t pos = teco_interface_ssm(SCI_GETCURRENTPOS, 0, 0);
- //teco_interface_ssm(SCI_DELWORDLEFTEND, 0, 0);
- teco_interface_ssm(SCI_WORDLEFTEND, 0, 0);
- if (pos == teco_interface_ssm(SCI_GETCURRENTPOS, 0, 0))
- break;
- teco_interface_ssm(SCI_DELWORDRIGHTEND, 0, 0);
+ while (n++) {
+ sptr_t old_pos = start_pos;
+ start_pos = teco_interface_ssm(SCI_WORDSTARTPOSITION, start_pos, TRUE);
+ start_pos = teco_interface_ssm(SCI_WORDSTARTPOSITION, start_pos, FALSE);
+ if (start_pos == old_pos)
+ return TECO_FAILURE;
}
}
- teco_interface_ssm(SCI_ENDUNDOACTION, 0, 0);
- if (n >= 0) {
- if (size != teco_interface_ssm(SCI_GETLENGTH, 0, 0)) {
- teco_interface_ssm(SCI_UNDO, 0, 0);
- teco_interface_ssm(SCI_GOTOPOS, pos, 0);
- }
- return TECO_FAILURE;
- }
- g_assert(size != teco_interface_ssm(SCI_GETLENGTH, 0, 0));
+ g_assert(start_pos < end_pos);
+ teco_interface_ssm(SCI_BEGINUNDOACTION, 0, 0);
+ teco_interface_ssm(SCI_DELETERANGE, start_pos, end_pos-start_pos);
+ teco_interface_ssm(SCI_ENDUNDOACTION, 0, 0);
if (teco_current_doc_must_undo()) {
undo__teco_interface_ssm(SCI_GOTOPOS, pos, 0);
diff --git a/tests/testsuite.at b/tests/testsuite.at
index 3f0b7e5..4d66392 100644
--- a/tests/testsuite.at
+++ b/tests/testsuite.at
@@ -113,6 +113,11 @@ AT_SETUP([Convert between line and glyph positions])
AT_CHECK([$SCITECO -e "@I/1^J2^J3/J 2^QC :^Q-3\"N(0/0)'"], 0, ignore, ignore)
AT_CLEANUP
+AT_SETUP([Deleting words])
+AT_CHECK([$SCITECO -e "@I/deleting words is useful/3J 2V .-3\"N(0/0)' Z-13\"N(0/0)'"], 0, ignore, ignore)
+AT_CHECK([$SCITECO -e "@I/deleting words is useful/3R 2Y .-14\"N(0/0)' Z-17\"N(0/0)'"], 0, ignore, ignore)
+AT_CLEANUP
+
AT_SETUP([Searches])
# FIXME: We cannot currently easily insert a single ASCII 5 (^E), as it must be followed
# by a 2nd character. It can be quoted, but cannot be written as Caret+E.