Cursor movement 11
Bindings the manual prints with an ESC- prefix are sequences: press Esc, release it, then press the key. Holding Alt instead works when the terminal sends Alt as an Esc prefix; the manual itself names the alt key for the numeric argument.
| Action | Emacs keymap |
|---|---|
| Back one charMoves the cursor one character to the left. | Ctrl+B |
| Cursor leftRuns the same widget as Ctrl + B, bound through the sequence the terminal reports for its left cursor key. | Left |
| Forward one charMoves the cursor one character to the right. | Ctrl+F |
| Cursor rightRuns the same widget as Ctrl + F; the manual shows the VT100 form of this cursor key as ESC-[C. | Right |
| Back one wordLands on the first character of the word before the cursor. | EscthenB |
| Forward one wordJumps to the start of the following word; the WORDCHARS parameter decides which characters count as part of a word. | EscthenF |
| Start of linePressed again at the start, it goes on to the start of the line above in a multi-line buffer. | Ctrl+A |
| End of lineAt the end already, it moves on to the last position of the following line, if one exists. | Ctrl+E |
| Find next characterWaits for one more key, then moves to where that character next appears in the line. | Ctrl+XthenCtrl+F |
| Go to columnTakes the column number from a numeric argument typed beforehand. | Escthen| |
| Match bracketJumps to the partner of the brace, parenthesis or square bracket at the cursor; elsewhere it first looks ahead for one. | Ctrl+XthenCtrl+B |
Deleting and yanking text 12
Ctrl + ? stands for the Delete character, which the manual writes as ^?. Many terminals send that character, and others Ctrl + H, when Backspace is pressed.
Ctrl + D is normally also the end-of-file character. Zsh exits on end-of-file unless the IGNORE_EOF option is set, and with it set still exits after ten in a row.
| Action | Emacs keymap |
|---|---|
| Delete previous charRemoves the character to the left of the cursor; the second binding is the Delete character, written ^? in the manual. | Ctrl+HorCtrl+? |
| Delete char or list choicesRemoves the character at the cursor; with the cursor after the last character it lists completions for the current word. | Ctrl+D |
| Delete word beforeKills the word to the left of the cursor, so a yank can bring it back. | Ctrl+WorEscthenCtrl+HorEscthenCtrl+? |
| Delete word afterA kill, not a plain delete: the current word goes to the kill buffer. | EscthenD |
| Kill to endKills from the cursor to the line end; already there, it kills the newline character instead. | Ctrl+K |
| Kill whole lineTakes only the current line; Ctrl + X, Ctrl + K is the widget for the entire buffer. | Ctrl+U |
| Kill bufferKills everything in the editing buffer, every line of a multi-line command included. | Ctrl+XthenCtrl+K |
| Yank killed textPuts the most recently killed text back in at the cursor. | Ctrl+Y |
| Yank popRight after a yank, swaps the inserted text for the previous entry of the kill ring; repeat to go further back. | EscthenY |
| Set markDrops the mark where the cursor is; the region between mark and cursor becomes active. | Ctrl+@ |
| Exchange point and markSwaps the cursor with the mark and activates the region between the two for highlighting. | Ctrl+XthenCtrl+X |
| Copy regionPlaces the text between cursor and mark in the kill buffer and leaves the line as it is. | EscthenW |
Editing text 13
| Action | Emacs keymap |
|---|---|
| Transpose charsSwaps the character at the cursor with its left neighbour; at the end of a line it swaps the last two. | Ctrl+T |
| Transpose wordsSwaps the current word with the word in front of it. | EscthenT |
| Capitalize wordApplies to the current word and leaves the cursor after it. | EscthenC |
| Lowercase wordTurns every letter of the current word into lower case, then steps past the word. | EscthenL |
| Uppercase wordTurns the current word into capitals and puts the cursor behind it. | EscthenU |
| Copy previous wordInserts a second copy of the word just before the cursor. | EscthenCtrl+_ |
| Join linesMerges the current line of a multi-line buffer with the one below it. | Ctrl+XthenCtrl+J |
| Toggle overwrite modeSwitches typing between overwriting and inserting; a second press switches back. | Ctrl+XthenCtrl+O |
| Quoted insertTakes the next character typed literally, so a control character lands in the buffer; an interrupt character is still not inserted. | Ctrl+V |
| Quote lineWraps the current line in single quotes and escapes the single quotes already inside it. | Escthen' |
| Quote regionWorks on the text between the mark and the cursor instead of the full line. | Escthen" |
| Insert tab or newlinePuts the control character typed after Esc into the buffer; a carriage return (Ctrl + M) is stored as a line feed. | EscthenCtrl+IorEscthenCtrl+JorEscthenCtrl+M |
| Undo last changeWorks step by step: each press takes back one more modification of the text. | Ctrl+_orCtrl+XthenUorCtrl+XthenCtrl+U |
History 13
Ctrl + S and Ctrl + Q are usually the terminal's stop and start characters. They reach the editor once flow control is switched off there with unsetopt FLOW_CONTROL.
| Action | Emacs keymap |
|---|---|
| Previous commandRecalls the previous history event once the cursor is on the top line of the buffer; before that it moves up a line. | Ctrl+P |
| Line up or previous commandThe up cursor key runs the same widget as Ctrl + P. | Up |
| Next commandMoves down a line inside a multi-line buffer and, from the bottom line, on to the next history event. | Ctrl+N |
| Line down or next commandThe down cursor key runs the same widget as Ctrl + N. | Down |
| Buffer start or oldest historyJumps to the first position of the buffer; pressed there, it loads the oldest entry of the history list. | Escthen< |
| Buffer end or newest historyJumps to the last position of the buffer first, and from there to the newest history event. | Escthen> |
| Search historySearches older entries as you type; lower-case search text ignores case, and a leading ^ anchors the match to the line start. | Ctrl+RorCtrl+XthenR |
| Search history forwardThe same incremental search toward newer entries, with the same editing keys in its mini-buffer. | Ctrl+SorCtrl+XthenS |
| History search backwardLooks through older history for a line that starts with the first word now in the buffer. | EscthenP |
| History search forwardMatches on the first word of the buffer as well, but moves toward newer history lines. | EscthenN |
| Infer next historyFinds a history line identical to the current one and fetches the event that came after it. | Ctrl+XthenCtrl+N |
| Insert last argumentInserts the final word of the previous history event; pressed again, it swaps in the final word of the event before. | Escthen.orEscthen_ |
| Run line and fetch nextRuns the current line, then puts the history event that follows it on the buffer stack for the next prompt. | Ctrl+O |
Completion and expansion 6
| Action | Emacs keymap |
|---|---|
| Expand or completeExpands the current word where the shell can, and otherwise attempts completion. | Tab |
| List choicesShows the possible completions of the current word. | EscthenCtrl+D |
| Expand historyResolves the history references in the edit buffer in place, before the line is run. | EscthenSpaceorEscthen! |
| Expand wordApplies shell expansion to the word at the cursor; unlike Tab it does not go on to completion. | Ctrl+Xthen* |
| List expansionDisplays what the current word would expand to. | Ctrl+XthenG |
| Correct spelling of wordAttempts the correction on the current word only. | Escthen$orEscthenS |
Running commands 6
| Action | Emacs keymap |
|---|---|
| Accept lineEnds editing and normally runs the buffer as a shell command; Ctrl + M is the character sent by Return. | Ctrl+JorCtrl+M |
| Accept and holdRuns the buffer and also keeps it on the buffer stack, so the same text is loaded at the next prompt. | EscthenA |
| Push lineClears the buffer and saves it on the buffer stack; the next time the editor starts, the saved text is loaded again. | Ctrl+QorEscthenQ |
| Get lineBrings back the most recently pushed line from the buffer stack, inserting it at the cursor. | EscthenG |
| Run helpSaves the buffer, then runs run-help for the command being typed; run-help is normally an alias for man. | EscthenH |
| Which commandSaves the buffer, then runs which-command on the current command; by default that is an alias for whence. | Escthen? |
Editor control and arguments 8
| Action | Emacs keymap |
|---|---|
| Clear screenClears the terminal and redraws the prompt. | Ctrl+LorEscthenCtrl+L |
| Send breakAborts the running editor function or, outside one, the line itself, which stays available in ZLE_LINE_ABORTED. | Ctrl+GorEscthenCtrl+G |
| Execute named commandPrompts for a widget name in a mini-buffer and runs that widget. | EscthenX |
| Repeat last named commandRuns again the widget most recently called through Esc, X. | EscthenZ |
| Digit argumentStarts a numeric argument or appends a digit to it; most widgets then repeat that many times. | Escthen0-9 |
| Negative argumentMakes the numeric argument typed next negative. | Escthen- |
| Enter vi command modeLeaves the emacs keymap and selects vicmd, the keymap of vi command mode. | Ctrl+XthenCtrl+V |
| Show cursor positionPrints the character at the cursor with its code in octal, decimal and hexadecimal, plus the buffer position and column. | Ctrl+Xthen= |
No row on this page matches that filter.
Notes
You are editing with Emacs bindings
Zsh's line editor (ZLE) starts in Emacs keymap for most setups, which is why these keys look familiar to Bash users: Ctrl + A and Ctrl + E jump to the ends of the line, Esc, F / Esc, B step by words (Esc first, then the letter — or hold Alt where the terminal sends it as an Esc prefix), Ctrl + F / Ctrl + B by characters. The deletion keys are kills, not deletes: Ctrl + U kills the whole line, Ctrl + K to the end, Ctrl + W the word behind, Esc, D the word ahead — and everything killed lands in a ring that Ctrl + Y yanks back. Cut-and-paste on the command line, no mouse involved. Ctrl + _ undoes edits.
History is the other half: Ctrl + R opens incremental search, Ctrl + P / Ctrl + N walk previous and next commands, and Esc, . inserts the last argument of the previous command — press it repeatedly to reach earlier commands' arguments. Tab completes, Ctrl + L clears the screen without losing your input.
The two keys people underuse
Esc, Q (push-line) stashes whatever you are typing, gives you a fresh prompt to run something else — check a path, read a man page — and restores your original line afterwards, untouched. It removes the classic dilemma of abandoning a half-written command. And know Ctrl + D's double life: with text on the line it deletes the character under the cursor (at the very end of the text it lists completions instead); on an empty line it sends end-of-file and exits the shell — the source of many accidentally closed terminals.
Questions
These bindings don't work in my zsh. Why?
You are probably in the Vi keymap — zsh selects it automatically when your VISUAL or EDITOR variable contains vi (vi, vim, nvim). Run bindkey -e to switch to Emacs bindings (add it to ~/.zshrc to make it stick), or embrace bindkey -v and use Vi-style editing instead.
What is the difference between killing and deleting?
Killed text (Ctrl + U, Ctrl + K, Ctrl + W, Esc, D) is saved to the kill ring and can be reinserted with Ctrl + Y — it is cut, not destroyed. Plain character deletion is gone for good (though Ctrl + _ can undo the edit).
Why does the table say Esc where I expected Alt, and why does Alt do nothing on my Mac?
The zsh manual prints these bindings with an Esc prefix: Esc, F is Esc pressed and released, then F. Holding Alt gives the same result only when the terminal sends Alt as that Esc prefix. macOS terminals type accented characters on Option by default; in Terminal.app or iTerm2, enable the profile setting that uses Option as Meta (Esc+), and Option with F, B or . starts working immediately.
When would I actually use Esc, Q?
Mid-command realisations: you are halfway through a long command and need to check a filename or free disk space first. Esc, Q stashes the line, you run the check, and the stashed command reappears at the next prompt ready to finish — no copy-paste, nothing lost.
Ctrl + D just closed my terminal. Can I prevent that?
On an empty line Ctrl + D means end-of-file, which ends the shell. Add setopt IGNORE_EOF to ~/.zshrc and zsh will ignore it (asking you to type exit instead; ten in a row still exit), while keeping the delete-character behaviour when the line has content.
Sources and checks
- Zsh manual 5.9.2 — Zsh Line Editor, section Standard Widgets (manual source file Doc/Zsh/zle.yo) Every widget with a default binding in the emacs keymap, and what each widget does
- zsh 5.9.2 source code — Src/Zle/zle_keymap.c (default key bindings) Arrow keys of the emacs keymap
- Zsh manual 5.9.2 — Options (manual source file Doc/Zsh/options.yo) FLOW_CONTROL and IGNORE_EOF options (table notes)
Every row on this page was matched to a line in the documentation above on . A binding that could not be found there is not listed.
Found a wrong or missing key? Tell us and it gets checked against the source. How we verify describes the process and its limits.