Skip to main content

AppEffect

Enum AppEffect 

Source
pub enum AppEffect {
Show 166 variants Quit, Cancel, FormatRange { intent: FormatIntent, start_line: u32, end_line: u32, }, MatchBracket, ToggleCaseAtCursor, OpenLineBelow, OpenLineAbove, SearchNext, SearchPrevious, JumpHistoryBack, JumpHistoryForward, PaneHistoryBack, PaneHistoryForward, WalkMarkHistoryBack, WalkMarkHistoryForward, TagStackPop, OpenFoldAtCursor, CloseFoldAtCursor, ToggleFoldAtCursor, OpenAllFolds, CloseAllFolds, CycleFoldAtCursor, CycleFoldsGlobal, GotoParentFold, DeleteFoldAtCursor, OpenFoldsRecursively, CloseFoldsRecursively, DeleteFoldsRecursively, GotoNextFold, GotoPrevFold, ToggleFoldEnable, Undo, Redo, RepeatLastChange, PageDown, HalfPageDown, HalfPageUp, PageUp, ScrollLineUp, ScrollLineDown, RedrawScreen, OpenCommandPicker, OpenHistoryPicker, OpenSearchHistoryPicker, EnterCommandLine, CommandLineSubmit, CommandLineCancel, CommandLineHistoryPrev, CommandLineHistoryNext, CommandLineComplete, CommandLineCompletePrev, CommandLineDescribeUnderCursor, CommandLineToggleExpand, SearchLineSubmit, SearchLineCancel, SearchLineBackspace, SearchLineHistoryPrev, SearchLineHistoryNext, SearchLineToggleExpand, PromptLineSubmit, PromptLineCancel, OilNavigateUp, ReselectLastVisual, SwapVisualEnds, PasteAfter, PasteBefore, EnterAppend, EnterInsertFirstNonBlank, EnterAppendEndOfLine, DisplayLineDown, DisplayLineUp, DisplayLineStart, DisplayLineEnd, CreateFoldFromVisual, CreateFold { start_line: u32, end_line: u32, }, DeleteCharBackward, InsertLineEdit(InsertLineEdit), CompletionTrigger, ExitVisual, ReplaceUndoLast, EnterMode(ModalState), EnterVisual(VisualKind), EnterSelect(VisualKind), EnterSearch(SearchDirection), SearchWordUnderCursor(SearchDirection), JumpViewport(ViewportPos), ScrollCursorTo(ScrollPos), HorizontalScroll(HScroll), JoinLines { with_space: bool, }, FindRepeat { reverse: bool, }, InsertNewline, InsertTab, OverwriteChar(char), SetMark(char), JumpToMarkLine(char), JumpToMarkExact(char), SelectRegister(Register), StartMacroRecord(char), PlayMacro(char), PlayLastMacro, AbsorbOperatorPrefix(OperatorId), SplitPaneHorizontal, SplitPaneVertical, ClosePane, OnlyPane, ToggleZoomPane, NavigatePane(PaneDirection), NextPane, PrevPane, NextTab, PrevTab, GoToTab(u32), NewTab, NewTabAt(String), TerminalSpawn(Option<String>), TerminalSpawnInNewTab(Option<String>), MovePaneToNewTab, CloseTab, OnlyTab, MoveTab(u32), PickerAcceptInSplit, PickerAcceptInVSplit, PickerAcceptInTab, EqualizePanes, GrowPaneHeight, ShrinkPaneHeight, GrowPaneWidth, ShrinkPaneWidth, CompletionNext, CompletionPrev, CompletionAccept, CompletionCancel, CompletionCancelAndExitInsert, CompletionToggleDocs, CompletionDocsScrollDown, CompletionDocsScrollUp, CompletionAcceptThenInsert(char), InsertRegister(char), OpenYankPicker, OpenArgPicker, SnippetNextPlaceholder, SnippetPrevPlaceholder, CompletionFilterToSource(String), CompletionFilterClear, DiffGet, DiffPut, TutorAdvance, TutorRetreat, MultibufferExpand { delta: i32, }, NarrowTrigger { range: Option<Range>, }, NarrowWiden, NarrowLines { start_line: u32, end_line: u32, }, SearchTrigger { query: String, }, SearchRefresh, CompileRun { cmdline: Option<String>, }, CompileJumpToLocation { path: PathBuf, line: u32, col: u32, }, ErrorNav { target: ErrorTarget, }, SetErrorList { source: ErrorSource, write: ErrorWrite, entries: Vec<ErrorEntry>, }, CompilationGutterSet { buffer: u32, entries: Vec<(u32, ErrorSeverity)>, }, CompilationLocationLines { buffer: u32, lines: Vec<(u32, u32, u32)>, }, CompilationThemeColors { bg: u32, fg: u32, }, CompilationKill, ProblemsOpen, ProblemsClose, ProblemsRefresh, OpenProviderView { provider: String, args: Args, },
}
Expand description

Variants are added incrementally during slice 8.i as each historical Action variant is promoted from the legacy bind_legacy bridge to a typed CommandInvocation.

Eq was dropped in PV.1 (2026-08-12), deliberately. Self::OpenProviderView carries an Args so a provider’s trigger keeps the typed multi-argument shape the : line and transient rows already produce — and Args reaches ArgValue::Invocation(Box<CommandInvocation>), which is PartialEq but not Eq. The alternative (flattening the payload to a Option<String>) would force every provider to re-encode structured arguments as strings, which is the stringly-typed weakness the seam exists to avoid. Nothing keys a map or set on AppEffect; PartialEq is what the round-trip tests use.

Variants§

§

Quit

Graceful editor shutdown. The App’s apply_effect arm publishes Event::BeforeQuit and sets the should_quit flag the runtime polls between frames; matches today’s Action::Quit semantics exactly. (8.i.0 smoke variant.)

CM.3d (2026-07-22) unbound the <C-c> → quit hatch that used to be hardcoded in input.rs; action:quit is now reachable only through :q and user bindings.

§

Cancel

CG.1: foreground cancellation. Flips the token of the in-flight user-initiated async op (search scan, LSP command, plugin call) and snaps the editor back to a stable Normal state. Bound to <C-c> at the Builtin layer in every mode, and to <C-g> by emacs-keys-mode.

Idempotent: with no op armed it degrades to the mode reset alone, which is why it is safe as a universal binding. See docs/dev/architecture/cancellation.md.

§

FormatRange

RF.5b: an operator resolved its range and the buffer’s chain for that intent says a non-native provider owns it.

The operator cannot run one itself — an LSP round-trip and a process spawn are both asynchronous, and the grammar layer has neither client nor runtime. So it returns the range and the host resolves the chain, exactly as SearchTrigger hands back a query rather than running a search.

Emitted only when the winning rung is not native, so the default configuration never produces one and the common path is unchanged.

Fields

§intent: FormatIntent

Which kind of formatting the operator asked for (= indent, gq reflow, g= reformat); selects the provider chain.

§start_line: u32

Inclusive 0-based line span.

§end_line: u32

Last line of the span (inclusive, 0-based).

§

MatchBracket

Vim’s %. Jumps to the bracket / brace / paren matching the one at-or-after the cursor on the current line. Promoted from Action::MatchBracket in slice 8.i.1.a.

§

ToggleCaseAtCursor

Vim’s ~. Toggles the case of the char at the cursor and advances by one byte. Promoted from Action::ToggleCaseAtCursor in slice 8.i.1.a.

§

OpenLineBelow

Vim’s o. Opens a new line below the current line and enters Insert. Promoted from Action::OpenLineBelow in slice 8.i.1.a.

§

OpenLineAbove

Vim’s O. Opens a new line above the current line and enters Insert. Promoted from Action::OpenLineAbove in slice 8.i.1.a.

§

SearchNext

Vim’s n. Re-runs the last search forward. Promoted from Action::SearchNext in slice 8.i.1.b.

§

SearchPrevious

Vim’s N. Re-runs the last search in the reverse direction. Promoted from Action::SearchPrevious in slice 8.i.1.b.

§

JumpHistoryBack

Vim’s <C-o>. Walk one step backward through the position history (DESIGN.md §5.1.1). Promoted from Action::JumpHistoryBack in slice 8.i.1.b.

§

JumpHistoryForward

Vim’s <C-i> / <Tab>. Walk one step forward through the position history. Promoted from Action::JumpHistoryForward in slice 8.i.1.b.

§

PaneHistoryBack

PBH.3: <C-6>. Walk one step back through the active pane’s buffer trail — the buffers this pane has shown.

Distinct from Self::JumpHistoryBack (<C-o>), which walks the global position ring at position granularity. This one is per-pane and moves whole buffers. See docs/dev/architecture/pane-buffer-history.md.

§

PaneHistoryForward

PBH.3: <C-7>. Walk one step forward through the active pane’s buffer trail.

§

WalkMarkHistoryBack

Vim’s g;. Walk one step backward through the mark history (oldest -> newest cursor positions in this buffer). Promoted from Action::WalkMarkHistoryBack in slice 8.i.1.b.

§

WalkMarkHistoryForward

Vim’s g,. Walk one step forward through the mark history. Promoted from Action::WalkMarkHistoryForward in slice 8.i.1.b.

§

TagStackPop

Vim’s <C-t>. Pop one entry off the tag stack and jump back to where the previous gd / <C-]> originated. Promoted from Action::TagStackPop in slice 8.i.1.b.

§

OpenFoldAtCursor

Vim’s zo. Open the fold containing the cursor. Promoted from Action::OpenFoldAtCursor in slice 8.i.1.c.

§

CloseFoldAtCursor

Vim’s zc. Close the fold containing the cursor. Promoted from Action::CloseFoldAtCursor in slice 8.i.1.c.

§

ToggleFoldAtCursor

Vim’s za. Toggle the fold containing the cursor. Promoted from Action::ToggleFoldAtCursor in slice 8.i.1.c.

§

OpenAllFolds

Vim’s zR. Open every fold in the buffer. Promoted from Action::OpenAllFolds in slice 8.i.1.c.

§

CloseAllFolds

Vim’s zM. Close every fold in the buffer. Promoted from Action::CloseAllFolds in slice 8.i.1.c.

§

CycleFoldAtCursor

org-cycle z<Space> / :fold-cycle. Cycle the heading/fold under the cursor through emacs org-mode’s local states FOLDED → CHILDREN → SUBTREE.

§

CycleFoldsGlobal

org-cycle z<Tab> / :fold-cycle-global. Cycle the WHOLE buffer through OVERVIEW → CONTENTS → SHOW-ALL.

§

GotoParentFold

zp / :fold-goto-parent. Move the cursor to the parent heading (one level up the fold hierarchy) — emacs outline-up-heading.

§

DeleteFoldAtCursor

Vim’s zd. Delete the fold containing the cursor (drop it from the manual fold table; structure-driven folds reappear on the next reparse). Promoted from Action::DeleteFoldAtCursor in slice 8.i.1.c.

§

OpenFoldsRecursively

VM.3h: vim’s zO. Open every fold containing the cursor line and every fold nested inside those. In Visual, the same over each selected line.

§

CloseFoldsRecursively

VM.3h: vim’s zC. Close every fold containing the cursor line, and nothing nested below the cursor. In Visual, every fold containing a selected line, enclosing ones included.

§

DeleteFoldsRecursively

VM.3h: vim’s zD. Delete the innermost fold containing the cursor line and every fold nested inside it. In Visual, the folds inside the selection, not the ones that merely enclose it.

§

GotoNextFold

Vim’s zj. Move cursor to the start of the next fold. Promoted from Action::GotoNextFold in slice 8.i.1.c.

§

GotoPrevFold

Vim’s zk. Move cursor to the end of the previous fold. Promoted from Action::GotoPrevFold in slice 8.i.1.c.

§

ToggleFoldEnable

Vim’s zi. Toggle the foldenable option (when off, every line renders flat regardless of any closed flag). Promoted from Action::ToggleFoldEnable in slice 8.i.1.c.

§

Undo

Vim’s u. Undo the last buffer change. Promoted from Action::Undo in slice 8.i.1.d.

§

Redo

Vim’s <C-r>. Redo the last undone change. Promoted from Action::Redo in slice 8.i.1.d.

§

RepeatLastChange

Vim’s .. Repeat the last change (operator + motion + register + count). Promoted from Action::RepeatLastChange in slice 8.i.1.d.

§

PageDown

Vim’s <C-f>. Page-down: scroll the viewport down one page. Promoted from Action::PageDown in slice 8.i.1.d.

§

HalfPageDown

VM.3j-2: vim’s <C-d> / <C-u> — scroll the view and the cursor together by scroll lines (half the window by default). SCROLL commands, not motions: vim composes no operator with them.

§

HalfPageUp

Vim’s <C-u>; the upward twin of Self::HalfPageDown.

§

PageUp

Vim’s <C-b>. Page-up: scroll the viewport up one page. Promoted from Action::PageUp in slice 8.i.1.d.

§

ScrollLineUp

Vim’s <C-y>. Scroll viewport up one line (cursor stays at the same screen position when possible). Promoted from Action::ScrollLineUp in slice 8.i.1.d.

§

ScrollLineDown

Vim’s <C-e>. Scroll viewport down one line. Promoted from Action::ScrollLineDown in slice 8.i.1.d.

§

RedrawScreen

Vim’s <C-l>. Force a full screen redraw. Promoted from Action::RedrawScreen in slice 8.i.1.e.

§

OpenCommandPicker

Vim’s : / Emacs’ M-x. Open the command picker over all registered ex-commands. If the chosen command has a required first argument the picker arms the cmdline so the user can supply it; otherwise executes immediately.

§

OpenHistoryPicker

MB.3: Vim’s q:. Open the command-line history picker over command_history. <CR> loads the chosen command into the : line WITHOUT executing (the user tweaks / <C-x><C-e> expands, then <CR>s). Fired from an ordinary buffer’s Normal mode or the expanded tier-2 band’s Normal mode (where it seeds the picker filter with the in-progress command-line text).

§

OpenSearchHistoryPicker

MB.5: q/ / q? — open the search-line history picker. Accept loads the chosen term into the / search line.

§

EnterCommandLine

Vim’s :. Enter the command-line minibuffer. Promoted from Action::EnterCommandLine in slice 8.i.1.e.

§

CommandLineSubmit

MB.1: <CR> in command-line-mode — submit (or accept the open completion candidate). Drives the rewired Editor::do_command_line_submit.

§

CommandLineCancel

MB.1: <Esc> / <C-c> in command-line-mode — cancel (or dismiss the open completion popup first).

§

CommandLineHistoryPrev

MB.1: <C-p> / <Up> in command-line-mode — walk history backward (or previous completion candidate when the popup is open).

§

CommandLineHistoryNext

MB.1: <C-n> / <Down> in command-line-mode — walk history forward (or next completion candidate when the popup is open).

§

CommandLineComplete

MB.1: <Tab> in command-line-mode — open the completion popup or advance the selection.

§

CommandLineCompletePrev

MB.1: <S-Tab> in command-line-mode — previous completion candidate.

§

CommandLineDescribeUnderCursor

MB.1: <C-h> in command-line-mode — describe the command / arg under the cursor.

§

CommandLineToggleExpand

MB.2: <C-x><C-e> in command-line-mode — toggle the : line’s expanded tier-2 mini-buffer band (full modal editing in place), or collapse it back to the one-row readline line for review.

§

SearchLineSubmit

MB.5a: <CR> on the /·? search line — submit the search pattern. Resolved from search-line-mode’s Insert keymap.

§

SearchLineCancel

MB.5a: <Esc> / <C-c> on the /·? search line — cancel the search and restore the prior editing buffer.

§

SearchLineBackspace

<BS> on the /·? line: delete a char, or cancel when empty.

§

SearchLineHistoryPrev

MB.5b: <C-p> / <Up> on the /·? search line — walk to an older entry in search_history.

§

SearchLineHistoryNext

MB.5b: <C-n> / <Down> on the /·? search line — walk to a newer entry in search_history.

§

SearchLineToggleExpand

MB.5c: <C-x><C-e> on the /·? search line — toggle the expanded tier-2 mini-buffer band.

§

PromptLineSubmit

<CR> in prompt-line-mode (Effect::OpenPrompt’s generic one-line text prompt) — submit the typed text to whichever action:* handler the caller named as on_submit_action. Drives Editor::do_prompt_line_submit.

§

PromptLineCancel

<Esc> / <C-c> in prompt-line-mode — cancel without firing anything, restore the prior editing buffer.

§

OilNavigateUp

Lattice’s -. Open / step up in the oil-style directory view (DESIGN.md §5.9.4). Promoted from Action::OilNavigateUp in slice 8.i.1.e.

§

ReselectLastVisual

Vim’s gv. Reselect the last Visual selection (same kind, anchor, head). Promoted from Action::ReselectLastVisual in slice 8.i.1.e.

§

SwapVisualEnds

Vim’s o in Visual mode – swap the cursor (head) to the other end of the selection (and back). Anchor and head trade places so subsequent motions / text objects grow or shrink the selection at the end the cursor now sits on.

§

PasteAfter

Vim’s p. Paste the unnamed register’s contents after the cursor. Promoted from Action::PasteAfter in slice 8.i.1.e.

§

PasteBefore

Vim’s P. Paste the unnamed register’s contents before the cursor. Promoted from Action::PasteBefore in slice 8.i.1.e.

§

EnterAppend

Vim’s a. Move cursor one byte right (clamped) and enter Insert. Promoted from Action::EnterAppend in slice 8.i.1.g.

§

EnterInsertFirstNonBlank

Vim’s I: move cursor to first non-blank column of the current line and enter Insert.

§

EnterAppendEndOfLine

Vim’s A: move cursor to end of the current line and enter Insert.

§

DisplayLineDown

Vim’s gj: move down one display line (wrap segment). Degrades to j when wrapping is off.

§

DisplayLineUp

Vim’s gk: move up one display line (wrap segment). Degrades to k when wrapping is off.

§

DisplayLineStart

Vim’s g0: move to the first byte of the current display segment. Degrades to 0 when wrapping is off.

§

DisplayLineEnd

Vim’s g$: move to the last byte of the current display segment. Degrades to $ when wrapping is off.

§

CreateFoldFromVisual

Vim’s zf. Create a fold from the most recent Visual selection. Promoted from Action::CreateFoldFromVisual in slice 8.i.1.g.

§

CreateFold

VM.3h: vim’s zf operator (zf{motion}, {Visual}zf). A CLOSED fold over the pre-resolved inclusive 0-based lines. Carries the span, so it crosses WIT like NarrowLines.

Fields

§start_line: u32

First line of the fold (0-based, inclusive).

§end_line: u32

Last line of the fold (0-based, inclusive).

§

DeleteCharBackward

Insert mode’s <BS>. Delete the byte before the cursor. Promoted from Action::DeleteCharBackward in slice 8.i.1.g.

§

InsertLineEdit(InsertLineEdit)

Insert-mode line editing — the readline/vim chords (<C-a>, <C-e>, <C-w>, <C-u>, <C-k>, <C-t>, <C-d>, …) available in every buffer. One grouped effect keyed by InsertLineEdit so the whole family shares a single host handler.

§

CompletionTrigger

Insert mode’s <C-Space> and <C-x><C-o>. Trigger the completion popup (omni-completion alias). Promoted from Action::CompletionTrigger in slice 8.i.1.g. The completion-popup minor-mode layer’s <C-Space> binding keeps its legacy bind_action registration until that helper picks up CommandInvocation (separate scope).

§

ExitVisual

Visual mode’s <Esc> / v / V. Exit Visual to Normal, collapsing the selection. Promoted from Action::ExitVisual in slice 8.i.1.h.

§

ReplaceUndoLast

Replace mode’s <BS>. Undo the last overwritten char. Promoted from Action::ReplaceUndoLast in slice 8.i.1.h.

§

EnterMode(ModalState)

Vim’s i / R / <Esc> (from Insert / Replace) – enter the named modal state. Promoted from Action::EnterMode(_) in slice 8.i.2.a. Each chord in the keymap binds a distinct CommandId whose ActionSpec returns the right AppEffect::EnterMode(state) constant – the ModalState rides in the AppEffect rather than in CommandInvocation::args so the App’s apply_app_effect matches a single EnterMode(state) arm instead of N param-flat variants.

§

EnterVisual(VisualKind)

Vim’s v / V / <C-v> – enter Visual with the named kind anchored at the current cursor. Promoted from Action::EnterVisual(_) in slice 8.i.2.a. Same encoding as Self::EnterMode: distinct CommandId per kind, payload rides in the AppEffect.

§

EnterSelect(VisualKind)

Vim’s gh / gH / g<C-h> – enter Select mode (SN.3d) with the named kind, anchored at the current cursor. Same encoding as Self::EnterVisual: distinct CommandId per kind, payload rides in the AppEffect. The host handler (do_enter_select) anchors a zero-width selection like do_enter_visual does — typing then overtypes it. Programmatic entry (snippets) instead uses EnterMode(Select(k)) with an explicit selection already set; see docs/dev/architecture/select-mode.md §3.

§

EnterSearch(SearchDirection)

Vim’s / / ? – enter the Search minibuffer in the named direction. Promoted from Action::EnterSearch(_) in slice 8.i.2.b. Same encoding as Self::EnterMode: distinct CommandId per direction.

§

SearchWordUnderCursor(SearchDirection)

Vim’s * / # – search for the word under the cursor in the named direction. Promoted from Action::SearchWordUnderCursor(_) in slice 8.i.2.b.

§

JumpViewport(ViewportPos)

Vim’s H / M / L – jump cursor to the named position within the visible viewport. Promoted from Action::JumpViewport(_) in slice 8.i.2.c.

§

ScrollCursorTo(ScrollPos)

Vim’s zz / zt / zb – scroll the viewport so the cursor’s current line sits at the named position. Promoted from Action::ScrollCursorTo(_) in slice 8.i.2.c.

§

HorizontalScroll(HScroll)

HS.2: vim z{l,h,L,H,s,e} manual horizontal scroll.

§

JoinLines

Vim’s J (with-space) / gJ (no-space). Joins the current line with the next, replacing the joining newline with a single space (with_space: true) or nothing (false). Promoted from Action::JoinLines in slice 8.i.2.d. Bool payload rides in the AppEffect: distinct CommandId per binding (J -> with-space=true, gJ -> with-space=false).

Fields

§with_space: bool

true for J (joined with a space), false for gJ (no space inserted).

§

FindRepeat

Vim’s ; (forward) / , (reverse). Repeat the most recent f / F / t / T find on the current line in the originally-typed direction (reverse: false) or the opposite direction (reverse: true). Promoted from Action::FindRepeat in slice 8.i.2.d.

Fields

§reverse: bool

false for ; (same direction as the original find), true for , (opposite direction).

§

InsertNewline

Insert / Replace mode’s <CR>. Inserts a literal newline at the cursor. Promoted from Action::Insert("\n".into()) in slice 8.i.2.e. Distinct flat variant rather than a String-payload Insert(_) because the keymap-bound forms always pin a fixed literal; the wildcard “type any printable char” path stays on Action::Insert(c.to_string()) since it isn’t keymap-bound.

§

InsertTab

Insert mode’s <Tab>. Inserts a literal tab at the cursor. Promoted from Action::Insert("\t".into()) in slice 8.i.2.e.

§

OverwriteChar(char)

Replace mode’s bare-printable wildcard. Overwrites the byte at the cursor with the captured char. Promoted from Action::OverwriteChar(c) in slice 8.i.3.

§

SetMark(char)

Vim’s m<X>. Sets mark <X> at the cursor’s current position. Promoted from Action::SetMark(c) in slice 8.i.3. The bound ActionSpec validates that <X> is [a-zA-Z0-9] – invalid chars dispatch to Effect::None (effectively a no-op; App::apply clears the pending state on every Invoke).

§

JumpToMarkLine(char)

Vim’s '<X>. Jumps the cursor to the line of mark <X>. Promoted from Action::JumpToMarkLine(c) in slice 8.i.3.

§

JumpToMarkExact(char)

Vim’s `<X>. Jumps the cursor to the exact position (line + byte) of mark <X>. Promoted from Action::JumpToMarkExact(c) in slice 8.i.3.

§

SelectRegister(Register)

Vim’s "<X>. Selects the named register for the next yank / paste / delete. Promoted from Action::SelectRegister(_) in slice 8.i.3. The bound ActionSpec validates the captured char via Register::from_input_char; chars that don’t name a register dispatch to Effect::None.

§

StartMacroRecord(char)

Vim’s q<X>. Starts recording a macro into register <X>. Promoted from Action::StartMacroRecord(c) in slice 8.i.3.

§

PlayMacro(char)

Vim’s @<X> for <X> alphanumeric. Plays the macro stored in register <X>. Promoted from Action::PlayMacro(c) in slice 8.i.3. The @@ chord is dispatched to Self::PlayLastMacro from the same play-macro action (the spec branches on the captured char).

§

PlayLastMacro

Vim’s @@. Replays the most recently played macro. Promoted from Action::PlayLastMacro in slice 8.i.3. Shares its bind site (@<CharLiteral>) with Self::PlayMacro; the play-macro action’s apply closure picks one or the other based on the captured char.

§

AbsorbOperatorPrefix(OperatorId)

Slice 8.i.4.c: arm an operator-pending state via the partial_chord mechanism. The App handler does two things atomically:

  1. Latch pending_count into op_count (vim’s <count>op<motion> count multiplication; without this 2dd would get a count of 1).
  2. Push the operator’s chord prefix into App::partial_chord so the next keystroke routes through lookup_normal_with_prefix and resolves [op, motion] / [op, i/a, text-object] / [op, f/F/t/T, char] to the bound Invoke.

Replaces the Action::SetPending(Pending::AfterOperator(_)) flow that did the same two things split across the keymap (which fired SetPending) and App::apply (which latched op_count inside the SetPending arm). The 8 operator prefixes – d, c, y, >, <, gU, gu, g~ – bind to typed actions whose ApplySpec returns this variant.

§

SplitPaneHorizontal

Vim’s <C-w>s: split the active pane horizontally. Promoted from Action::SplitPaneHorizontal in slice 8.i.4.d.

§

SplitPaneVertical

Vim’s <C-w>v: split the active pane vertically. Promoted from Action::SplitPaneVertical in slice 8.i.4.d.

§

ClosePane

Vim’s <C-w>c / <C-w>q: close the active pane. Promoted from Action::ClosePane in slice 8.i.4.d.

§

OnlyPane

Vim’s <C-w>o / :only / emacs C-x 1: close every pane except the active one (collapse the tree to the active leaf). No-op when only one pane is open. S3b (2026-06-22).

§

ToggleZoomPane

ZP.2: <C-w>z / <C-w><C-z> / :zoom-pane — toggle tmux-style zoom on the active pane. Non-destructive, unlike Self::OnlyPane: the split layout is preserved and the second toggle restores it verbatim. No-op on a single-pane tab. See docs/dev/architecture/pane-zoom.md.

§

NavigatePane(PaneDirection)

Vim’s <C-w>h/j/k/l (and arrow / <BS> aliases): move focus to the pane in the named direction. Promoted from Action::NavigatePane(_) in slice 8.i.4.d.

§

NextPane

Vim’s <C-w>w / <C-w><Tab>: cycle focus to the next pane. Promoted from Action::NextPane in slice 8.i.4.d.

§

PrevPane

Vim’s <C-w>W / <C-w><S-Tab>: cycle focus to the previous pane. Promoted from Action::PrevPane in slice 8.i.4.d.

§

NextTab

Issue #29 (2026-05-22): vim’s gt — next tab.

§

PrevTab

Vim’s gT — previous tab.

§

GoToTab(u32)

Vim’s {N}gt — switch to tab N (1-indexed; clamped).

§

NewTab

:tabnew — new empty tab.

§

NewTabAt(String)

:tabnew <path> — new tab opening path.

§

TerminalSpawn(Option<String>)

Issue #40 / Terminal-mode T1 (2026-05-22): :terminal [cmd] — spawn a PTY-backed shell.

§

TerminalSpawnInNewTab(Option<String>)

T4 (2026-05-25): :tabterminal [cmd] — open a fresh tab and spawn a PTY-backed shell in it. Handler does do_new_tab then do_terminal_spawn(cmd).

§

MovePaneToNewTab

T4 (2026-05-25): <C-w>T — move the active pane to a fresh tab. Handler in Editor::do_move_pane_to_new_tab.

§

CloseTab

:tabclose — close active tab.

§

OnlyTab

:tabonly — close every tab except the active one.

§

MoveTab(u32)

:tabmove [N] — move active tab to position N (1-indexed).

§

PickerAcceptInSplit

Issue #32 (2026-05-22): picker open-target overrides. <C-s> — accept selected candidate in horizontal split.

§

PickerAcceptInVSplit

<C-v> — accept selected candidate in vertical split.

§

PickerAcceptInTab

<C-t> — accept selected candidate in new tab.

§

EqualizePanes

Issue #28 (2026-05-22): <C-w>= — reset every split’s ratio to 0.5.

§

GrowPaneHeight

<C-w>+ — grow the active pane vertically.

§

ShrinkPaneHeight

<C-w>- — shrink the active pane vertically.

§

GrowPaneWidth

<C-w>> — grow the active pane horizontally.

§

ShrinkPaneWidth

<C-w>< — shrink the active pane horizontally.

§

CompletionNext

Completion-popup overlay: focus the next entry. Promoted from Action::CompletionNext in slice 8.i.4.e.

§

CompletionPrev

Completion-popup overlay: focus the previous entry. Promoted from Action::CompletionPrev in slice 8.i.4.e.

§

CompletionAccept

Completion-popup overlay: accept the focused candidate. Promoted from Action::CompletionAccept in slice 8.i.4.e.

§

CompletionCancel

Completion-popup overlay: cancel the popup, stay in Insert. Promoted from Action::CompletionCancel in slice 8.i.4.e.

§

CompletionCancelAndExitInsert

Completion-popup overlay: cancel the popup and exit Insert. Promoted from Action::CompletionCancelAndExitInsert in slice 8.i.4.e.

§

CompletionToggleDocs

Completion-popup overlay: toggle the doc-popup (<C-d>). Promoted from Action::CompletionToggleDocs in slice 8.i.4.e.

§

CompletionDocsScrollDown

Completion-popup overlay: scroll the doc-popup down (<C-f>). Promoted from Action::CompletionDocsScrollDown in slice 8.i.4.e.

§

CompletionDocsScrollUp

Completion-popup overlay: scroll the doc-popup up (<C-b>). Promoted from Action::CompletionDocsScrollUp in slice 8.i.4.e.

§

CompletionAcceptThenInsert(char)

Completion-popup overlay: bare-printable wildcard. Accept the focused candidate, then insert the captured char (so the user can finish typing through a confirmed prefix). Promoted from Action::CompletionAcceptThenInsert(c) in slice 8.i.4.e.

§

InsertRegister(char)

YR.5: vim’s insert-register — <C-r> then a register char, inserting that register’s contents at the cursor.

§

OpenYankPicker

YR.5: <C-r><C-r> — open the yank-ring picker, filling whichever surface it was opened from.

§

OpenArgPicker

YR.6: open the picker registered for the :-line argument under the cursor (ArgSpec.picker), filling the pick back into it.

§

SnippetNextPlaceholder

Active-snippet overlay: jump to the next placeholder (<Tab>). Promoted from Action::SnippetNextPlaceholder in slice 8.i.4.e.

§

SnippetPrevPlaceholder

Active-snippet overlay: jump to the previous placeholder (<S-Tab>). Promoted from Action::SnippetPrevPlaceholder in slice 8.i.4.e.

§

CompletionFilterToSource(String)

Completion-popup overlay: restrict candidates to a single source. The string is the SourceId (e.g. "gen:buffer-words", "gen:lsp-completion"). Bound to the popup-mode filter chords (<C-b>, <C-o>, <C-f>, <C-t>, …) introduced in CSM.K2.

§

CompletionFilterClear

Completion-popup overlay: clear the active source filter (<C-Space>). Restores the mixed merged candidate list.

§

DiffGet

D.5.b (2026-05-30): diff-mode do (diff-get) operator. CR.1 (2026-06-24): do is now mode-owned (DiffMode::action_handlers() → Effect::ApplyEdit); this AppEffect is retained only as the FALLBACK the action:diff-get CommandSpec emits when no handler is registered. The host’s apply_app_effect arm is emptied to a silent no-op (the Action::DiffGet variant it used to push is deleted).

§

DiffPut

D.5.c (2026-05-30): diff-mode dp (diff-put) operator. CR.1: mirror of Self::DiffGet — mode-owned now; retained as the emptied action:diff-put fallback shell.

§

TutorAdvance

T.3: tutor-mode <CR> / :tutor-next. Advance to the next exercise; advance to the next lesson when the current one is complete. No-op when tutor-mode is not active on the current buffer.

§

TutorRetreat

T.3: tutor-mode :tutor-prev. Retreat to the previous exercise. No-op at exercise 0.

§

MultibufferExpand

M.5 (2026-06-01): :multibuffer-expand [n] / :multibuffer-contract [n] ex-commands. delta is the signed row count (positive expands, negative contracts). Routed to the active multibuffer view’s expand_excerpt_at from the dispatch path. No-op when the active buffer isn’t a multibuffer.

Fields

§delta: i32

Context lines to add (positive) or remove (negative) around the excerpt under the cursor.

§

NarrowTrigger

N.1.1 (2026-06-10): :narrow [{range}] ex-command. The host arm resolves range against the active document to a line span, fetches the active buffer’s Arc<dyn Document>, and calls lattice_multibuffer::providers::narrow::create_narrow_view — opening a one-excerpt multibuffer focused on that region. range == None (bare :narrow) narrows the current paragraph (blank-line delimited, vim’s ip).

Fields

§range: Option<Range>

The unresolved : range, resolved by the host against cursor, last Visual selection and marks (see crate::Range for which forms resolve); None = current paragraph.

§

NarrowWiden

N.1.1 (2026-06-10): :widen ex-command. The host arm closes the active narrow view (an editable one-excerpt multibuffer), restoring the full source buffer. No-op + echo when the active buffer isn’t a narrow view.

§

NarrowLines

N.1.3 (2026-06-10): the zn narrow operator emits this once the operator-pending machinery has resolved its motion / text object to a line span. Carries pre-resolved inclusive 0-based [start_line, end_line] (unlike NarrowTrigger, which carries an unresolved Range); the host arm narrows the active buffer to that span via the same create_narrow_view sink.

Fields

§start_line: u32

First line of the region (0-based, inclusive).

§end_line: u32

Last line of the region (0-based, inclusive).

§

SearchTrigger

M.6 (2026-06-01): :search <query> ex-command. M.10.6 (2026-06-03) inlined the work into the host’s apply_effect arm — it calls lattice_multibuffer::providers::search::project_search against the active editor as the activator. No longer trampolines through Action::SearchTrigger / Editor::do_search (both deleted).

Fields

§query: String

The search query, passed to the project-search provider as typed.

§

SearchRefresh

M.6.1 (2026-06-01): gr chord in project-search-mode. Re-runs the scan with the view’s current query. M.10.5 (2026-06-03) made this mode-owned: the search mode’s on_activate registers a closure that intercepts via ActionHandlerRegistry before this AppEffect arm runs. The arm is a no-op marker; the work happens in the mode’s closure (reading state, clearing excerpts, spawning a fresh scan task).

§

CompileRun

CM.1 (2026-07-21): :compile <cmd> / :recompile / :make. The host arm creates the read-only synthetic *compilation* buffer host-side (Editor::ensure_named_synthetic_document, activating compilation-mode) and kicks off the pipe-captured off-thread run via the CompilationServiceHandle, whose output streams into that buffer. Same shape as SearchTrigger: the substrate crate owns the work; the host arm is generic apply-effect routing. cmdline: Some(cmd) for :compile; None for :recompile / bare :make (reuse the last command).

Fields

§cmdline: Option<String>

Shell command line to run; None re-runs the last one.

§

CompileJumpToLocation

CM.3b (2026-07-22): <CR> on a location line in the *compilation* buffer. The compilation-mode action handler parses the cursor line’s text (parse_location_line) into a source location and emits this; the host arm calls Editor::jump_to_file_line_col(&path, line, col) (records the hop in position history) and syncs the error list index to the matching entry. line / col are 0-based. The location rides in the AppEffect because the jump target is computed off the buffer text in the mode’s closure, but the error list index is core/host state — so the host owns the apply.

Fields

§path: PathBuf

File to open (activated if already open).

§line: u32

0-based line; clamped to the file’s last line.

§col: u32

0-based byte column; clamped to the line’s length.

§

ErrorNav

CM.2 (2026-07-22): :cnext/:cprev/:cc [N]/:cfirst/ :clast and the Builtin ]q/[q chords. The host arm calls Editor::do_error_nav, which walks the core error list (recording each hop in position history via jump_to_file_line_col). On an empty list every target echoes “no error list” and moves nothing – there is no fallback to diagnostic hopping (]d / [d own that).

Fields

§target: ErrorTarget

Which entry to jump to.

§

SetErrorList

CM.3a (2026-07-22): parsed error entries from the compilation stderr reader — the off-thread → host-state seam. The reader accumulates entries and sends the FULL list through the compilation inbound bus; this handler maps each send here, and the host arm calls Editor::set_error_list(entries) (replace-semantics — the growing list stays visible). An empty vec (sent on a new run / :recompile) clears the stale list. The parser (below-host lattice-compilation) and this payload share the lattice_protocol::error_list::ErrorEntry type.

Fields

§source: ErrorSource

EP.1 (2026-08-10): which producer this run came from. The host arm replaces only this source’s slice, so a language server republishing on edit-debounce cannot wipe a compile run’s entries while the user walks them.

§write: ErrorWrite

EP.2: new run (reset the index) vs live refresh (re-anchor it). Declared by the producer — not inferrable from the entries.

§entries: Vec<ErrorEntry>

The source’s complete entry list (replace, not append). Empty clears this source’s slice.

§

CompilationGutterSet

CM.3c (2026-07-22): the per-buffer severity gutter index for the *compilation* buffer — the off-thread → host-state seam for in-buffer severity marks (twin of SetErrorList, which feeds the cross-file error list). The compilation drain scans each streamed line for a severity keyword, accumulates the FULL per-buffer index of (line, severity), and sends it through the compilation inbound bus; this handler maps each send here, and the host arm converts the severities to GutterSeverityLevel and writes the render_state compilation-severity slot for buffer. The renderer reads that slot and injects it into the mode’s gutter_decorations via CompilationSeverityData. An empty vec (sent on Reset / a new run) clears the buffer’s marks.

buffer is the raw BufferId.0 (BufferId is process-local and not Serialize, so the wire form is the u32; the host arm reconstructs BufferId). Severity rides as the parser-native ErrorSeverity (already shared with SetErrorList) — the single map to the renderer-facing GutterSeverityLevel happens host-side, avoiding a lossy GutterSeverityLevel↔ErrorSeverity round-trip and keeping lattice-grammar free of a lattice-mode dependency.

Fields

§buffer: u32

BufferId.0 of the compilation buffer.

§entries: Vec<(u32, ErrorSeverity)>

(0-based line, severity) for every marked line; the full index, replacing the previous one.

§

CompilationLocationLines

CM.3c (2026-07-22): per-buffer compilation location-line index for theme-based highlighting of navigable lines in the *compilation* buffer. Twin of CompilationGutterSet: the off-thread compilation drain scans each chunk for location-bearing lines (via parse_location_line) and ships the full list through an inbound bus; this effect writes the render_state compilation-location slot for buffer. An empty vec (sent on Reset / a new run) clears the buffer’s location-line set.

Fields

§buffer: u32

BufferId.0 of the compilation buffer.

§lines: Vec<(u32, u32, u32)>

(line, path_byte_start, path_byte_end) for each location line. byte_start/end are the byte offsets of the file-path portion within the line text, for link-like fg highlighting.

§

CompilationThemeColors

CM.3d (2026-07-22): resolved compilation location theme colours — published by the mode during activation so the renderer reads compilation.location bg/fg from the theme rather than hardcoding RGB values.

Stored editor-wide (not per buffer); the latest send wins.

Fields

§bg: u32

Background of a location line, packed 0xRRGGBB.

§fg: u32

Foreground of a location line’s path, packed 0xRRGGBB.

§

CompilationKill

CM.3d (2026-07-22): kill the running compilation child process. The host arm calls CompilationService::kill().

§

ProblemsOpen

CM.4 (2026-07-22): :copen. The host arm reads the core error list and calls lattice_multibuffer::providers::problems::create_problems_view, opening the *problems* multibuffer — the error entries grouped as editable source excerpts by file. Same shape as SearchTrigger: the substrate crate owns view-creation; the host arm is generic apply-effect routing. Echoes “no error list” when the list is empty.

§

ProblemsClose

CM.4 (2026-07-22): :cclose. The host arm closes the active *problems* view (an editable multibuffer with ProblemsMinorMode), leaving the source buffers open — the NarrowWiden close shape, guarded to problems views. No-op + echo when the active buffer isn’t a problems view.

§

ProblemsRefresh

RV.3 (2026-08-10): gr in a *problems* view — rebuild its excerpts from the current error list, in place.

Deliberately NOT a re-fire of Self::ProblemsOpen: create_multibuffer_view mints a fresh BufferId on every call, so re-opening would leave the old view behind and add a second *problems* buffer rather than refreshing the one the user is looking at. The host arm instead re-reads the error list and hands it to lattice_multibuffer::providers::problems::refresh_problems_view, which swaps sources + excerpts atomically via replace_excerpts. Same division as ProblemsOpen: the substrate crate owns the rebuild, the host arm is generic glue.

§

OpenProviderView

PV.1 (2026-08-12): open the multibuffer view a provider owns — the generic replacement for the per-provider trigger variant.

A multibuffer view can only be created through ModeActivator, which is &mut-backed and therefore host-only, so every provider trigger has to round-trip through an effect. SearchTrigger / ProblemsOpen each spent a variant here plus a host match arm plus a plugin-boundary arm on exactly that — three crates touched per provider, against a design whose acid test is that a provider crate touches none.

Here the host arm is provider-agnostic: look provider up in the ProviderViewRegistry, call the registered opener with the host as the activator and args verbatim, then apply the generic outcome (activate + echo, or echo the refusal). What the opener computes, and how it words its own success and refusal, stays in the provider’s crate.

args is the trigger’s parameters as the : line or transient row produced them — the same Args shape a command handler receives, so one opener serves both front-ends.

:narrow / zn deliberately do NOT route through here; see Self::NarrowTrigger and lattice_mode::provider_view’s module docs for why a range resolved against cursor / Visual / marks is not a provider parameter.

Fields

§provider: String

Name the provider registered its opener under in the ProviderViewRegistry. An unknown name echoes a warning naming it.

§args: Args

The trigger’s parameters, passed to the opener verbatim.

Trait Implementations§

Source§

impl Clone for AppEffect

Source§

fn clone(&self) -> AppEffect

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl Debug for AppEffect

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<'de> Deserialize<'de> for AppEffect

Source§

fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>
where __D: Deserializer<'de>,

Deserialize this value from the given Serde deserializer. Read more
Source§

impl PartialEq for AppEffect

Source§

fn eq(&self, other: &AppEffect) -> bool

Equality operator ==. Read more
1.0.0 (const: unstable) · Source§

fn ne(&self, other: &Rhs) -> bool

Inequality operator !=. Read more
Source§

impl Serialize for AppEffect

Source§

fn serialize<__S>(&self, __serializer: __S) -> Result<__S::Ok, __S::Error>
where __S: Serializer,

Serialize this value into the given Serde serializer. Read more
Source§

impl StructuralPartialEq for AppEffect

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> DeserializeOwned for T
where T: for<'de> Deserialize<'de>,

Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

§

impl<T> Instrument for T

§

fn instrument(self, span: Span) -> Instrumented<Self> ⓘ

Instruments this type with the provided [Span], returning an Instrumented wrapper. Read more
§

fn in_current_span(self) -> Instrumented<Self> ⓘ

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
§

impl<T> WithSubscriber for T

§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self> ⓘ
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a [WithDispatch] wrapper. Read more
§

fn with_current_subscriber(self) -> WithDispatch<Self> ⓘ

Attaches the current default Subscriber to this type, returning a [WithDispatch] wrapper. Read more