Skip to content

Editing

Modes

Mode How you get there What it is for
Normal Esc, always Where the keys are commands. The editor starts here.
Insert i I a A o O s S c Typing text.
Visual v Selecting characters, then acting on the selection.
Visual line V The same, by whole lines.
Command : / ? The line at the bottom of the screen.

The status bar names the mode you are in, except normal, which says nothing because it is where you spend most of your time.

Ctrl+C does not quit. It says type :q to exit, which is vi's own answer.

The grammar

The whole of it is:

["x] [count] operator [count] motion

Everything follows from that. d is delete, w is a word, so dw deletes a word. 2dw and d2w both delete two. "ad2w deletes two words into register a.

Operators

d delete
c change: delete, then insert
y yank (copy)
> < indent, outdent by one unit of whatever the file indents with

Doubling an operator applies it to the whole line: dd, yy, cc, >>, <<.

Motions

h j k l left, down, up, right (arrow keys work too)
w b e word forwards, back, to the end
W B E the same, treating punctuation as part of the word
0 ^ $ the first column, the first non-blank, the end of the line
gg G the first line, the last
{ } back and forward a paragraph
f F t T to a character on this line, forwards or back, on it or just before
% to the bracket matching the next one on this line
`a 'a to a mark

j and k remember the column you were aiming for, so moving through a short line and out the other side puts you back where you were.

Text objects

An operator takes an object as readily as a motion. i is "inner" and a is "around", and the difference is whether the delimiters go too.

iw aw a word
iW aW a word, punctuation included
i( a( i) a) ib ab what is in the parentheses
i{ a{ i} a} iB aB in the braces
i[ a[ i] a] in the brackets
i" a" i' a' i` a`

ci" is the one to learn first: it changes the string you are standing in, whichever quote it is and wherever in it you are.

Single-key edits

x X delete the character under the cursor, or before it
D C delete or change to the end of the line
s S substitute the character, or the line
r replace one character with the next key you press
~ swap the case of the character
J join the next line onto this one; 3J joins three
p P put what was yanked, after the cursor or before
o O open a line below or above, keeping the indent

The indent o keeps is the one the line above is made of, so a tab-indented Makefile recipe stays tab-indented.

Registers

"x before a command sends its text to register x. With no register named, it goes to the unnamed one.

"ayy      yank this line into register a
"ap       put it back
"+y       yank to the system clipboard
"+p       put from it

The clipboard registers + and * are the system one, and go through a subprocess (see files and windows).

Undo

u undoes, Ctrl+R redoes. One u undoes one change, not one keystroke: everything you typed between i and Esc goes at once, and a :s over the whole file goes at once too.

Repeat

. repeats the last change. It is stored as the keystrokes that made it, as vi stores it, and that is why a command ending in insert mode replays whole: cwNEWEsc is one change, and replaying only the cw would leave you in insert mode with nothing typed.

Macros

. under a name and for as long as you like.

qa        start recording into register a
…         whatever you want recorded
q         stop
@a        play it
3@a       play it three times
@@        play the last one again

Macros share storage with the yank registers, the way vi's do: "ap pastes a macro as text, and @a runs a line you yanked. A macro that calls itself stops with a message before the stack runs out.

Marks

ma        put mark a on this line and column
`a        come back to the character
'a        come back to the first non-blank of that line
``        come back from the last jump
:marks    list them

The difference between ` and ' matters most with an operator in front: d`a takes characters, d'a takes whole lines.

Every jump (G, gg, a search, a %) leaves a mark behind, so `` returns from it.

One place this is smaller than vi

Marks are not shifted when the text above them moves. Insert ten lines above mark a and it still points at the same line number, not the same line.

Scrolling and paging

Ctrl+F Ctrl+B forward and back a screenful
Ctrl+D Ctrl+U half a screenful
Ctrl+E Ctrl+Y move the view without moving the cursor

A "screenful" is the window you are in, measured on the last frame, so it is right in a split and right on a tall terminal. Ctrl+E drags the cursor only when it has to, where Ctrl+D always takes it along. The point of the pair is to look at what is below without losing your place.

Long lines wrap onto the next screen line, and tabs are drawn out to their tab stops.