Skip to content

fix(vi): repaint whenever the mode changes - #1256

Merged
kronberger-droid merged 1 commit into
nushell:mainfrom
devtechedge:fix/vi-append-repaint
Oct 23, 2026
Merged

kronberger-droid merged 1 commit into
nushell:mainfrom
devtechedge:fix/vi-append-repaint

Conversation

@devtechedge

@devtechedge devtechedge commented Oct 16, 2026 •

Copy link
Copy Markdown
Contributor

Summary

Pressing a on an empty buffer switched Vi to insert mode, but the MoveRight it emits is Inapplicable since #1208.
Only handled events trigger a repaint, so the prompt kept showing the normal-mode indicator until the next keystroke.
A and I hit the same path when the cursor is already at the line end or start.
The real bug is that a mode change does not guarantee a repaint, so the fix sits in the Vi dispatch in vi/mod.rs, where changes_mode is applied.
Whenever the mode actually changes, Repaint is appended to the event, mirroring helix's Multiple([event, Repaint]) on next_mode.
Events that already end in Repaint (i, c<motion>) don't get a second one, and commands that report Normal from Normal (dw, yy) get none.
Leaving Visual for Normal now repaints as well.
No public API change.

Before

Empty line, Esc shows NORMAL>, then a still shows NORMAL> until a character is typed.

After

a, A and I show INSERT> right away, as does every other mode switch.

Additional notes

Dispatch tests cover entering insert, no duplicate Repaint, and no spurious Repaint when staying in Normal.
Fixes #1255

@devtechedge
devtechedge force-pushed the fix/vi-append-repaint branch from 5d989ff to 71d842d Compare October 16, 2026 17:25
@kronberger-droid

Copy link
Copy Markdown
Collaborator

Hmm, but i think the fix belongs one layer down.
The bug is that a mode change does not guarantee a repaint, not these three commands.
Helix already handles it at dispatch: every action with a next_mode gets wrapped as Multiple([event, Repaint]) in helix/mod.rs.
Can you do the same in vi/mod.rs where changes_mode is applied, and append Repaint whenever the mode actually changes?

@kronberger-droid
kronberger-droid marked this pull request as draft October 18, 2026 11:05
@devtechedge
devtechedge force-pushed the fix/vi-append-repaint branch from 71d842d to 11a3d90 Compare October 18, 2026 14:30
@devtechedge
devtechedge marked this pull request as ready for review October 18, 2026 14:30
@devtechedge

devtechedge commented Oct 18, 2026 •

Copy link
Copy Markdown
Contributor Author

Thanks for the steer - a mode change not guaranteeing a repaint is the real bug here.

I have moved the repaint into vi/mod.rs, where changes_mode is applied.

It now appends Repaint only when the new mode differs from the previous one, mirroring the Helix next_mode wrap.

The per-command repaints for a, A, and I are gone.

Tests now cover this at the dispatch level, including commands that stay in normal mode not gaining a spurious repaint.

This is amended into the original commit as 11a3d90, and the PR is ready for review again.

@kronberger-droid

Copy link
Copy Markdown
Collaborator

Thanks thats what I had in mind.

@kronberger-droid kronberger-droid changed the title fix(vi): repaint when a, A or I enter insert mode without moving the cursor fix(vi): repaint whenever the mode changes Oct 23, 2026
@kronberger-droid
kronberger-droid merged commit 7701cb0 into nushell:main Oct 23, 2026
8 checks passed
@kronberger-droid

Copy link
Copy Markdown
Collaborator

I just updated the body and title so if one comes back to it, it reflects the new structure. Hope thats fine for you.

@devtechedge

Copy link
Copy Markdown
Contributor Author

Thanks a lot, Martin, for steering this one down to the dispatch layer!

Pointing at how Helix wraps every next_mode action with a Repaint turned a three-command patch into a fix for the real bug, so every Vi mode switch now repaints 🙂

I also appreciate you retitling the PR and reworking the description so the history reads right for whoever lands here next.

It was a pleasure working through this with you on reedline 🚀

@kronberger-droid

Copy link
Copy Markdown
Collaborator

Sure, was a pleasure.

kronberger-droid added a commit to nushell/nushell that referenced this pull request Oct 25, 2026
## Description

Bumps reedline to `c8d81b2`, five PRs past `39db5e3`:

- nushell/reedline#1256 `fix(vi): repaint whenever the mode changes`
- nushell/reedline#1244 `feat(hints): let hinters and highlighters
handle hints before auto-pair closers`
- nushell/reedline#1261 `fix(menu): take the partial completion across
all suggestion spans`
- nushell/reedline#1263 `fix(engine): treat Ctrl+J as a line ending when
draining the input batch`
- nushell/reedline#1257 `feat(external_printer): ungate the printer and
commit messages in one frame`

`#1244` replaces the unreleased `#1239` behavior with hooks that default
to the last release, so hints before auto-pair closers come back with
#19199

`#1261` only changes the partial reedline derives itself, and nushell
passes its own, so `foo re<Tab>` keeps its current behavior until the
nushell side follows

### User-facing changes (Release notes)

- Fixed the vi prompt indicator not switching to insert on `a`, `A` or
`I` when the cursor does not move.
- Fixed piped input with several LF-terminated lines dropping every line
after the first.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Vi Mode: Pressing a on an Empty Buffer Does not Repaint the Mode Indicator

2 participants