Vim is a modal editor, meaning its behavior changes based on the current mode—no mouse required!
| Mode | Enter | Exit | Purpose |
|---|---|---|---|
| Normal | Esc / Ctrl+[ |
— | Navigation & commands (default) |
| Insert | i, a, o |
Esc |
Typing text |
| Visual | v, V, Ctrl+V |
Esc |
Text selection |
| Replace | R |
Esc |
Overwrite existing text |
| Command | : |
Enter |
Ex commands (:w, :q, etc.) |
Mode Context Examples:
- Normal mode:
dddeletes a line, but in Insert mode types "dd" - Visual mode: select text with movement keys, then operate on selection
- Replace mode: typing replaces existing characters (useful for tables)
h/j/k/l: ← ↓ ↑ →w: jump to start of next wordb: jump to start of previous worde: move to end of current wordge: move to end of previous word*/#: search forward/backward for word under cursorW/B/E: same asw/b/ebut for WORDS (space-separated)
Examples:
- In
hello_worldwith cursor ath,wjumps to_, butWjumps to next space
0/^/$: line start / first non-blank / line endgg/G: first line / last line:n/nG: go to line n (e.g.:5or10G)%: jump to matching bracket ((),{},[]){/}: jump to previous/next paragraphH/M/L: jump to Home/Middle/Last line of visible screen
Examples:
- In
function() {, pressing^from start jumps tof - With cursor on
{, press%to jump to matching}
Ctrl+u/Ctrl+d: scroll up/down half-pageCtrl+b/Ctrl+f: scroll up/down full-pagezt/zz/zb: move current line to top / center / bottom of screen
f{c}/F{c}: forward/backward to{c}on linet{c}/T{c}: forward/backward until before{c};/,: repeat lastf/tforward/backward
Examples:
- In
function(arg), with cursor atf, typef(to jump to( - Then
;to jump to next(if any on the line
Ctrl+o/Ctrl+i: jump backward/forward through positions:jumps: display jump list
g;/g,: jump to the last change (backward/forward)]m/[m: jump to the start of the next/previous method or function]/[: jump to the next/previous unmatched[{or]}:help motion.txt: explore all motion commands in Vim's help system
Examples:
- After editing multiple lines, use
g;to revisit the last change. - In a code file, use
]mto jump to the next function definition.
i/I: insert before cursor / at first non-blanka/A: insert after cursor / at end of lineo/O: open new line below / abovegi: resume insert at last insertion point
Examples:
A+ type;+Esc: add semicolon at end of lineO+ type// Comment+Esc: add comment above current line
x/X: delete character under/before cursordw/db: delete to start of next/previous worddd/D: delete entire line / to end of lined{motion}: delete text covered by{motion}di{/da{: delete inside/around curly braces (works with()[]<>"')
Examples:
d$: delete from cursor to end of lined2j: delete current line and 2 lines belowdit: delete inside HTML/XML tag
y{motion}/yyorY: yank text or linep/P: paste after / before cursor"ay{motion}/"ap: yank to register 'a' / paste from register 'a':reg: view all registers"0p: paste from yank register (not affected by deletes)
Examples:
yiwthen move cursor andp: duplicate word"ay3wthen"ap: yank 3 words into register 'a', then paste them
c{motion}/C: change text or to end of lines/S: substitute char & insert / substitute liner{c}: replace character under cursor with{c}R: enter replace mode~: toggle case of character under cursor
Examples:
ct): change text until next)(excl.)cw: change word (likedwtheni)cc: change entire line (likeddtheni)
u/Ctrl+r: undo / redo changesU: undo all changes on line.: repeat last change
v/V/Ctrl+V: character / line / block selectiongv: reselect last visual selection
Visual Block Examples:
Ctrl+V→ select multiple lines →I→ type text →Esc: insert at beginning of multiple linesCtrl+V→ select block →d: delete blockCtrl+V→ select block →r{c}: replace with character
Operate on semantic blocks using operator + text-object:
| Object | Inner (i) |
Around (a) |
|---|---|---|
| Word | iw |
aw |
| Sentence | is |
as |
| Paragraph | ip |
ap |
Quotes " |
i" |
a" |
| Parentheses | i( |
a( |
| Tags | it |
at |
Examples:
ci"changes inside quotes ("hello"→""with cursor between quotes)dapdeletes around paragraph (including trailing blank line)vibvisually select inside parenthesesya]yank around square brackets (including the brackets)ditdelete inside HTML/XML tag (leaves the tags intact)
Vim's search and replace feature is powerful and supports regular expressions.
/pattern/?pattern: Search forward / backward forpattern.n/N: Repeat the search forward / backward.:%s/old/new/g: Replace all occurrences ofoldwithnewin the file.:%s/old/new/gc: Replace all occurrences with confirmation.:%s/old/new/gi: Replace all occurrences, case-insensitive.
/\<word\>: Search for the exact wordword(not part of another word)./\d\+: Search for one or more digits./^\s*function: Search for lines starting withfunction(ignoring leading spaces).:%s/\(\w\+\)/"\1"/g: Surround every word with quotes.:g/TODO/d: Delete all lines containing "TODO".
Tip for Beginners: Use :set hlsearch to highlight search results and :noh to clear the highlights.
ma: set markaat cursor`a/'a: jump to exact position / line of marka`./'.: jump to last edit position / line`[/`]: jump to start/end of last change or yank`</`>: jump to start/end of last visual selection`0through`9: jump to position when Vim was last closed
Examples:
maat start of function,mzat end, then`aand`zto navigated'a: delete from current line to line marked withaya'b: yank text from markato markb`
Registers are like "named clipboards" in Vim. They store text for yanking, deleting, or copying. Here are the main types:
- Unnamed Register (
""): Stores the last deleted or yanked text. This is the default register used when no specific register is mentioned. - Numbered Registers (
"0to"9):"0: Stores the last yanked text."1to"9: Store the last nine deletions, with"1being the most recent.
- Named Registers (
"ato"z): Manually store text using"ay{motion}(e.g.,"aywyanks a word into registera). - System Clipboard (
"+): Interact with the system clipboard. Use"+yto copy to the clipboard and"+pto paste from it. - Black Hole Register (
"_): Discards text without saving it to any register. Useful for deleting without overwriting the unnamed register.
Examples:
- Yank text into a named register:
"ayw(yank a word into registera). - Paste from the system clipboard:
"+p. - Delete without saving:
"_dd(deletes the current line without affecting registers).
"{reg}y{motion}: yank into register {reg}"{reg}p: paste from register {reg}"+y{motion}/"+p: yank to / paste from system clipboard"_d{motion}: delete without saving to register (black hole)"0p: paste from yank register (not affected bydorc):reg: view register contents
Examples:
"ayythen"ap: copy line to registera, then paste it"+yG: yank from cursor to end of file to system clipboard"_dd: delete line without affecting registers (useful before pasting)
Macros allow you to record a sequence of commands and replay them.
q{reg}: Start recording a macro into register{reg}(e.g.,qastarts recording into registera).q: Stop recording.@{reg}: Execute the macro stored in register{reg}.@@: Repeat the last executed macro.{count}@{reg}: Execute the macro{count}times.
Examples:
-
Add a prefix to multiple lines:
qa→I//→Esc→j→q(record macro to add//at the start of a line).@ato apply the macro once, or10@ato apply it to 10 lines.
-
Format a list:
qa→0i-→Esc→j→q(record macro to add-at the start of a line).- Use
@ato repeat for a list of items.
Tip for Beginners: If you make a mistake while recording, press q to stop and start over.
-
Add a prefix to multiple lines:
qa→I//→Esc→j→q@ato apply once, or10@ato apply to 10 lines.
-
Format a list:
qa→0i-→Esc→j→q- Use
@ato repeat for a list of items.
-
Swap two words:
qa→diw→e→P→q- Use
@ato repeat the swap.
Folding allows you to collapse sections of text, making it easier to navigate large files.
zf{motion}: Create a fold for the specified motion (e.g.,zf%folds everything between matching brackets).zo/zc: Open / close a fold.zr/zm: Reduce / increase the fold level for the entire file.zR/zM: Open / close all folds.zj/zk: Move to the next / previous fold.
Examples:
- To fold a function:
- Place the cursor at the start of the function.
- Use
zf%to fold everything between the matching brackets.
- To open all folds:
zR. - To close all folds:
zM.
Tip for Beginners: If folding doesn't work, ensure :set foldmethod=manual or :set foldmethod=syntax is enabled.
:split/:vsplit: horizontal / vertical splitCtrl+w+h/j/k/l: navigate between windowsCtrl+w+_/|: maximize height/width of current windowCtrl+w+=: make all windows equal size:e file: edit file in new buffer:ls: list buffers:bn/:bp: next / previous buffer:bd: delete (close) buffer
Examples:
:vsplit index.js→Ctrl+w l→ edit in right window:ein insert mode completes filenames
- Delete a word:
This is a test|→dw→This is a | - Change inside quotes:
"Learn Vim|"→ci"→ typeMaster→"Master" - Jump to line 5:
5Gor:5 - Visual delete paragraph: place cursor in paragraph →
vap→d - Search & replace:
/foo→:%s/foo/bar/gc - Multi-line edit:
Ctrl+V→ select multiple lines →I→ type →Esc - Macro for formatting:
qa→0i- [ ] ^[j→q→10@a(adds checkboxes) - Double quoted string:
Hello→viw→S"→"Hello" - swap two words:
one two→dwelp→two one - Sort lines:
:'<,'>sortin visual selection
- vimtutor: built-in interactive tutorial (
vimtutor) - Vim Adventures: gamified learning at vim-adventures.com
- Vimcasts: free screencasts by Drew Neil for step-by-step demos (vimcasts.org)
- vim-wiki: comprehensive wiki at vimhelp.org
- Practical Vim by Drew Neil: excellent book for intermediate users
- Cheat Sheet: GitHub Gist with condensed commands
- vim-awesome.com: directory of plugins