Closed lobre closed 11 months ago
Hi,
Loric Brevet @.***> wrote:
As neatvi has neither a command history nor a
cedit
(like in nvi) to edit command history, how is your workflow to re-enter previous (or slightly modified previous) commands?I can see it has a special buffer
:
that contains the previous ex command, and it also has^p
to paste the default buffer in normal mode. So I am able to paste the default buffer in an ex command with^p
, but I cannot paste from other buffers (such as:
).Do you have a workaround to accomplish such a thing?
I have not found a clean solution yet. What I do now, if I need to redo or modify the last command, is to first paste it into a buffer, modify it, and copy it into the default yank buffer.
Ali
Would it make sense to implement ^R<reg>
in insert and command mode to insert the content of a register?
It would not help to modify the last command though as it would still require to paste it to a buffer for modification.
Loric Brevet @.***> wrote:
Would it make sense to implement
^R<reg>
in insert and command mode to insert the content of a register?
Done.
Ali
Thank you for quickly implementing this! I guess that now, using a custom buffer to deal with command history is handy enough 🎉.
Maybe having a mapping that executes the line under the cursor as a command could simplify the process even more. A bit the same as gf
for opening a file, but instead it would execute an ex command. That would avoid having to copy/paste into command mode. But this would maybe be going too far.
In the same vein, the plan 9 acme editor provides the developer with two main actions (triggered on mouse buttons 2 and 3 on a 3-button mouse) that either open the file under cursor (or currently selected) or "execute" the current line/word/selected text as a command.
Having something like this could help also to execute shell commands as one could write ex commands starting with an exclamation mark (e.g. :!ls -l
).
I see this system as having "good leverage with small footprint" as it would allow having interesting custom workflows just by leveraging buffers and ex commands. Something to dig!
Loric Brevet @.***> wrote:
Thank you for quickly implementing this! I guess that now, using a custom buffer to deal with command history is handy enough 🎉.
Maybe having a mapping that executes the line under the cursor as a command could simplify the process even more. A bit the same as
gf
for opening a file, but instead it would execute an ex command. That would avoid having to copy/paste into command mode. But this would maybe be going too far.
We already have @ normal mode command, which executes the contents of any register. We can introduce a special register for the current line; for instance = so that @= executes the current line. Any suggestions for the register name?
I first tried having a separate # command for executing the contents registers as ex commands; just like @, which is for vi commands. However, that does not seem necessary: if the register (or current line) begins with a colon, @ executes it as an ex command.
Ali
We already have @ normal mode command, which executes the contents of any register. We can introduce a special register for the current line; for instance = so that @= executes the current line.
This is smart! I do like when we avoid adding new features, but instead consolidate and integrate with concepts that are already existing. This is the elegance of a good design, empowering orthogonality and composition without adding too much overhead.
Any suggestions for the register name?
We could stay consistent with vim maybe for this?
": Contains the most recent executed command-line. Example: Use
"@:" to repeat the previous command-line command.
The command-line is only stored in this register when at least
one character of it was typed. Thus it remains unchanged if
the command was completely from a mapping.
In vim, =
is the expression register. I am not against using it, but using :
makes more sense to me as it represents the command line.
Loric Brevet @.***> wrote:
We could stay consistent with vim maybe for this?
": Contains the most recent executed command-line. Example: Use "@:" to repeat the previous command-line command. The command-line is only stored in this register when at least one character of it was typed. Thus it remains unchanged if the command was completely from a mapping.
In vim,
=
is the expression register. I am not against using it, but using:
makes more sense to me as it represents the command line.
This is for the previous command not the current line.
Ali
Sorry I misread your comment. If searching for a name that would best represent a line, maybe _
could be it (hence @_
).
The _
can be referenced as the "linewise" motion.
_ <underscore> [count] - 1 lines downward, on the first non-blank
More info about the ins and outs of this motion here:
https://vi.stackexchange.com/a/19746
I don't know if this translates fully to our exemple here but I don't find any other "obvious" names.
Maybe there is not such a thing and @=
might not be bad after all.
Loric Brevet @.***> wrote:
Sorry I misread your comment. If searching for a name that would best represent a line, maybe
_
could be it (hence@_
).The
_
can be referenced as the "linewise" motion._ <underscore> [count] - 1 lines downward, on the first non-blank
More info about the ins and outs of this motion here:
https://vi.stackexchange.com/a/19746
I don't know if this translates fully to our exemple here but I don't find any other "obvious" names.
Maybe there is not such a thing and
@=
might not be bad after all.
OK. I have assigned register ; to the current line. Now it is also possible to use %, " and . registers for the current file, the default yank buffer, and the last vi command, respectively.
Ali
This is neat, thank you! I will play with this.
When I build now, I do have warning though (simply using make
):
cc -c -Wall -O2 reg.c
reg.c: In function ‘reg_putraw’:
reg.c:38:18: warning: array subscript [-128, 255] is outside array bounds of ‘char *[256]’ [-Warray-bounds]
38 | free(bufs[tolower(c)]);
| ~~~~^~~~~~~~~~~~
reg.c:7:14: note: while referencing ‘bufs’
7 | static char *bufs[256];
| ^~~~
reg.c:39:13: warning: array subscript [-128, 255] is outside array bounds of ‘char *[256]’ [-Warray-bounds]
39 | bufs[tolower(c)] = buf;
| ~~~~^~~~~~~~~~~~
reg.c:7:14: note: while referencing ‘bufs’
7 | static char *bufs[256];
| ^~~~
And another question, how to represent the "escape" character in a written command in a register?
For example, I have this line that I could now execute with @;
:
cwnewword<esc>jdd
Is there a way to represent this <esc>
so that I go back to normal mode?
And same question for the newline character:
cwnewword\nandnewline<esc>
Here in my example \n
is literally entered, but I am searching for a way to enter a real newline character.
Sorry for the spam, I am just reporting while exploring ^^.
I see that the :
register does not work correctly when there are two splits. It does not contain the last command, but instead, it always contains e! unnamed
.
Loric Brevet @.***> wrote:
This is neat, thank you! I will play with this.
When I build now, I do have warning though (simply using
make
):cc -c -Wall -O2 reg.c reg.c: In function ‘reg_putraw’: reg.c:38:18: warning: array subscript [-128, 255] is outside array bounds of ‘char *[256]’ [-Warray-bounds] 38 | free(bufs[tolower(c)]); | ~~~~^~~~~~~~~~~~ reg.c:7:14: note: while referencing ‘bufs’ 7 | static char *bufs[256]; | ^~~~ reg.c:39:13: warning: array subscript [-128, 255] is outside array bounds of ‘char *[256]’ [-Warray-bounds] 39 | bufs[tolower(c)] = buf; | ~~~~^~~~~~~~~~~~ reg.c:7:14: note: while referencing ‘bufs’ 7 | static char *bufs[256]; | ^~~~
The compiler seems wrong.
Ali
Loric Brevet @.***> wrote:
And another question, how to represent the "escape" character in a written command in a register?
For example, I have this line that I could now execute with
@;
:cwnewword<esc>jdd
Is there a way to represent this
<esc>
so that I go back to normal mode?
You can use ^v^[.
And same question for the newline character:
cwnewword\nandnewline<esc>
Here in my example
\n
is literally entered, but I am searching for a way to enter a real newline character.
You cannot do that in a single line. You can store the multi-line command in a register and execute that.
Ali
Loric Brevet @.***> wrote:
Sorry for the spam, I am just reporting while exploring ^^.
I see that the
:
register does not work correctly when there are two splits. It does not contain the last command, but instead, it always containse! unnamed
.
That is the command neatvi executes to switch between buffers. Now it stores user commands only.
Ali
The compiler seems wrong.
Here is what I have.
$ which cc
/usr/bin/cc
$ ls -l /usr/bin/cc
lrwxrwxrwx 1 root root 20 Jul 20 15:12 /usr/bin/cc -> /etc/alternatives/cc
$ ls -l /etc/alternatives/cc
lrwxrwxrwx 1 root root 12 Jul 20 15:12 /etc/alternatives/cc -> /usr/bin/gcc
$ which gcc
/usr/bin/gcc
$ gcc --version
gcc (Ubuntu 11.4.0-1ubuntu1~22.04) 11.4.0
Copyright (C) 2021 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
I tried in an Alpine container and a fresh build system and it is all good. The issue seems to be on my NixOS box. So no red lights here in the end.
Your recent changes have an impact and enable an efficient editing workflow. Thank you a lot.
I still have a few remarks.
.
register? I mean it is cool to have access to the last vi command, but do you have an example in mind of where/when it could be useful?_
would be a better name as it reflects the "line" motion already present in vi
with d_
, y_
, ... Do you have a counter-argument or a reason to prefer ;
or is it arbitrary? On the flip side, I know that vim has the _
as being the "black-hole register", but I am not sure this is a necessary feature in neatvi.:
register containing the previous ex command. But this register does not contain the actual :
character. Which means one cannot simply reapply the latest command with @:
. That would be nice behavior though. If this is not desired, maybe there should be a special case which says that when applying this register with @
, a :
should be prepended?For this 3. nvi does have a command to reapply previous substitution:
& Repeat the previous substitution command on the current line.
But if we have @:
, that would be a superset of this feature, as we would be able to reapply the previous ex command to the current line generally speaking.
Loric Brevet @.***> wrote:
But if we have
@:
, that would be a superset of this feature, as we would be able to reapply the previous ex command to the current line generally speaking.
OK. Now Neatvi prefixes : register with a colon, to make repeating the previous ex command with @: possible.
Indeed. That makes @:
really smooth. Though on the flip side, it makes ^R:
more cumbersome when doing it in ex mode, because it will add two ::
. Not sure what could be done here.
Loric Brevet @.***> wrote:
Indeed. That makes
@:
really smooth. Though on the flip side, it makes^R:
more cumbersome when doing it in ex mode, because it will add two::
. Not sure what could be done here.
As ex ignores excess colons, it probably doesn't matter.
Ali
As ex ignores excess colons, it probably doesn't matter.
This can make sense.
Do you have other comments about command history in general (like things in the workflow that are required to slightly improve)? Or should I close this issue?
Loric Brevet @.***> wrote:
As ex ignores excess colons, it probably doesn't matter.
This can make sense.
Do you have other comments about command history in general (like things in the workflow that are required to slightly improve)? Or should I close this issue?
I cannot think of a simple, clean, and convenient improvement at the moment.
Ali
Ok, closing this issue then. Thank you again for all the work on this topic!
Hi,
As neatvi has neither a command history nor a
cedit
(like in nvi) to edit command history, how is your workflow to re-enter previous (or slightly modified previous) commands?I can see it has a special buffer
:
that contains the previous ex command, and it also has^p
to paste the default buffer in normal mode. So I am able to paste the default buffer in an ex command with^p
, but I cannot paste from other buffers (such as:
).Do you have a workaround to accomplish such a thing?
Thanks