Blame


1 031e20a5 2019-04-19 hi <p class="f7">
2 031e20a5 2019-04-19 hi <a href="/suggest.html">suggestion box</a> &ndash;
3 f63f6045 2024-11-11 mischa <a href="https://got.high5.nl/?action=summary&path=why-vi.rocks.git">latest additions (got)</a> &ndash;
4 031e20a5 2019-04-19 hi <a href="/also.html">see also</a> &ndash;
5 031e20a5 2019-04-19 hi <a href="/colophon.html">colophon</a>
6 031e20a5 2019-04-19 hi </p>
7 18871106 2019-04-06 git
8 bd65552c 2023-06-11 mischa <div class="logo-container">
9 bd65552c 2023-06-11 mischa <img id="logo" class="mt4" src="vi-sw.png" alt="Logo">
10 bd65552c 2023-06-11 mischa </div>
11 18871106 2019-04-06 git
12 f6e4de9c 2023-06-07 mischa _Why? [vi](https://en.wikipedia.org/wiki/Vi) is the **de facto** standard
13 031e20a5 2019-04-19 hi text editor in any Unix-like operating system._
14 7b150fff 2019-04-07 git
15 031e20a5 2019-04-19 hi Here is a collection of [vi(1)](https://man.openbsd.org/vi.1)/[ex(1)](https://man.openbsd.org/ex.1) commands and command sequences.<br>
16 031e20a5 2019-04-19 hi Tested with [nvi](https://en.wikipedia.org/wiki/Nvi) 1.79 and 2.1.3 (unicode).
17 7815de24 2019-04-10 git
18 c57b7323 2020-05-10 git [Bill Joy's greatest gift to man - the vi editor](https://www.theregister.co.uk/2003/09/11/bill_joys_greatest_gift/)
19 af599e02 2019-04-06 git
20 c57b7323 2020-05-10 git
21 031e20a5 2019-04-19 hi ## Yank/delete lines
22 18871106 2019-04-06 git
23 031e20a5 2019-04-19 hi (1) mark the first line: `mk`<br>
24 031e20a5 2019-04-19 hi (2) move to last line<br>
25 031e20a5 2019-04-19 hi (3a) yank: `y'k`<br>
26 031e20a5 2019-04-19 hi (3b) delete: `d'k`<br>
27 031e20a5 2019-04-19 hi (4) move to destination line<br>
28 031e20a5 2019-04-19 hi (5) put with `P` or `p`<br>
29 18871106 2019-04-06 git
30 18871106 2019-04-06 git
31 031e20a5 2019-04-19 hi ## Apply regex to lines
32 18871106 2019-04-06 git
33 031e20a5 2019-04-19 hi (1) mark the first line: `mk`<br>
34 031e20a5 2019-04-19 hi (2) mark the last line: `ml`<br>
35 66a0e66d 2019-04-06 git
36 031e20a5 2019-04-19 hi <pre>
37 031e20a5 2019-04-19 hi :'k,'ls/<em>regex</em>/<em>power</em>/g
38 031e20a5 2019-04-19 hi </pre>
39 66a0e66d 2019-04-06 git
40 66a0e66d 2019-04-06 git
41 50439ce0 2019-04-22 git ## Increment / Decrement number in command mode
42 50439ce0 2019-04-22 git
43 50439ce0 2019-04-22 git (1) move cursor to number<br>
44 50439ce0 2019-04-22 git (2a) increment by one: #+<br>
45 50439ce0 2019-04-22 git (2b) increment by N (5): 5#+<br>
46 50439ce0 2019-04-22 git (3a) decrement by one: #-<br>
47 50439ce0 2019-04-22 git (3b) decrement by N (9): 9#-
48 50439ce0 2019-04-22 git
49 50439ce0 2019-04-22 git
50 031e20a5 2019-04-19 hi ## Add &#35; to a block
51 031e20a5 2019-04-19 hi
52 031e20a5 2019-04-19 hi <pre>
53 031e20a5 2019-04-19 hi :'k,'ls/^/#/
54 031e20a5 2019-04-19 hi </pre>
55 031e20a5 2019-04-19 hi
56 031e20a5 2019-04-19 hi
57 c57b7323 2020-05-10 git ## Remove trailing whitespace from every line
58 c57b7323 2020-05-10 git
59 75e09f64 2020-07-19 git <pre>
60 75e09f64 2020-07-19 git :%s/ *$//
61 75e09f64 2020-07-19 git </pre>
62 c57b7323 2020-05-10 git
63 c57b7323 2020-05-10 git
64 64a200c4 2023-06-06 mischa ## Remove tabs
65 64a200c4 2023-06-06 mischa
66 64a200c4 2023-06-06 mischa <pre>
67 64a200c4 2023-06-06 mischa :%s/<u>&lt;CTRL-V&gt;&lt;TAB&gt;</u>//g
68 64a200c4 2023-06-06 mischa </pre>
69 64a200c4 2023-06-06 mischa
70 64a200c4 2023-06-06 mischa
71 031e20a5 2019-04-19 hi ## Remove trailing whitespace from a block
72 031e20a5 2019-04-19 hi
73 75e09f64 2020-07-19 git <pre>
74 75e09f64 2020-07-19 git :'k,'ls/\ *$//
75 75e09f64 2020-07-19 git </pre>
76 66a0e66d 2019-04-06 git
77 5717e66e 2019-04-15 git
78 50439ce0 2019-04-22 git ## Remove the first N-characters from every line
79 5717e66e 2019-04-15 git
80 031e20a5 2019-04-19 hi N = 5
81 f069fab6 2019-04-16 git
82 031e20a5 2019-04-19 hi <pre>
83 031e20a5 2019-04-19 hi :%s/^.\{0,<em>5</em>\}//
84 031e20a5 2019-04-19 hi </pre>
85 f069fab6 2019-04-16 git
86 f069fab6 2019-04-16 git
87 031e20a5 2019-04-19 hi ## Delete all lines N-character long
88 f069fab6 2019-04-16 git
89 031e20a5 2019-04-19 hi N = 10
90 a070b304 2019-04-08 git
91 031e20a5 2019-04-19 hi <pre>
92 031e20a5 2019-04-19 hi :g/^.\{<em>10</em>\}$/d
93 031e20a5 2019-04-19 hi </pre>
94 a070b304 2019-04-08 git
95 18871106 2019-04-06 git
96 031e20a5 2019-04-19 hi ## Delete all lines _except_ N-character long
97 031e20a5 2019-04-19 hi
98 031e20a5 2019-04-19 hi N = 10
99 031e20a5 2019-04-19 hi
100 031e20a5 2019-04-19 hi <pre>
101 031e20a5 2019-04-19 hi :g!/^.\{<em>10</em>\}$/d
102 031e20a5 2019-04-19 hi </pre>
103 031e20a5 2019-04-19 hi
104 031e20a5 2019-04-19 hi
105 031e20a5 2019-04-19 hi ## Search/replace paths using &#35; as delimiter
106 031e20a5 2019-04-19 hi
107 031e20a5 2019-04-19 hi <pre>
108 031e20a5 2019-04-19 hi :%s#<em>/usr/local/log</em>#<em>/var/log</em>#g
109 031e20a5 2019-04-19 hi </pre>
110 031e20a5 2019-04-19 hi
111 031e20a5 2019-04-19 hi
112 9122df5c 2023-06-06 mischa ## Search/replace &#94;M with LF
113 64a200c4 2023-06-06 mischa
114 9122df5c 2023-06-06 mischa <pre>
115 9122df5c 2023-06-06 mischa :g/<u>&lt;CTRL-V&gt;&lt;ENTER&gt;</u>/s///g
116 9122df5c 2023-06-06 mischa </pre>
117 64a200c4 2023-06-06 mischa
118 64a200c4 2023-06-06 mischa
119 031e20a5 2019-04-19 hi ## Write the file as root
120 031e20a5 2019-04-19 hi
121 18871106 2019-04-06 git :w !doas tee %
122 18871106 2019-04-06 git
123 18871106 2019-04-06 git
124 031e20a5 2019-04-19 hi ## Diff the file on disk with the buffer
125 031e20a5 2019-04-19 hi
126 18871106 2019-04-06 git :w !diff -u % -
127 18871106 2019-04-06 git
128 18871106 2019-04-06 git
129 031e20a5 2019-04-19 hi ## Make a backup of the file on disk
130 031e20a5 2019-04-19 hi
131 6c9b71bc 2019-04-06 git :!cp % %.bak
132 18871106 2019-04-06 git
133 18871106 2019-04-06 git
134 031e20a5 2019-04-19 hi ## Sort all lines
135 031e20a5 2019-04-19 hi
136 18871106 2019-04-06 git :%!sort
137 18871106 2019-04-06 git
138 18871106 2019-04-06 git
139 031e20a5 2019-04-19 hi ## Sort a block
140 6c9b71bc 2019-04-06 git
141 031e20a5 2019-04-19 hi `}` won't be shown
142 f931c46b 2019-04-07 git
143 031e20a5 2019-04-19 hi <pre>
144 190821ba 2019-04-20 git !<u>}</u>sort
145 031e20a5 2019-04-19 hi </pre>
146 9ad69938 2019-04-07 git
147 9ad69938 2019-04-07 git
148 031e20a5 2019-04-19 hi ## Sort from the current line to EOF
149 9ad69938 2019-04-07 git
150 031e20a5 2019-04-19 hi `G` won't be shown
151 6c9b71bc 2019-04-06 git
152 031e20a5 2019-04-19 hi <pre>
153 031e20a5 2019-04-19 hi !<u>G</u>sort
154 031e20a5 2019-04-19 hi </pre>
155 031e20a5 2019-04-19 hi
156 031e20a5 2019-04-19 hi
157 031e20a5 2019-04-19 hi ## Delete duplicated lines in the file
158 031e20a5 2019-04-19 hi
159 18871106 2019-04-06 git :%!uniq
160 18871106 2019-04-06 git
161 031e20a5 2019-04-19 hi ## Delete duplicated lines in the block
162 18871106 2019-04-06 git
163 031e20a5 2019-04-19 hi `}` won't be shown
164 6c9b71bc 2019-04-06 git
165 031e20a5 2019-04-19 hi <pre>
166 031e20a5 2019-04-19 hi !<u>}</u>uniq
167 031e20a5 2019-04-19 hi </pre>
168 f931c46b 2019-04-07 git
169 031e20a5 2019-04-19 hi ## Delete duplicated lines till EOF
170 9ad69938 2019-04-07 git
171 031e20a5 2019-04-19 hi `G` won't be shown
172 9ad69938 2019-04-07 git
173 031e20a5 2019-04-19 hi <pre>
174 031e20a5 2019-04-19 hi !<u>G</u>uniq
175 031e20a5 2019-04-19 hi </pre>
176 9ad69938 2019-04-07 git
177 9541feb7 2019-04-08 git
178 031e20a5 2019-04-19 hi ## Underline all lines starting with `pattern`
179 9541feb7 2019-04-08 git
180 031e20a5 2019-04-19 hi <pre>
181 031e20a5 2019-04-19 hi :g/^<em>pattern</em> /t.|s/./=/g
182 031e20a5 2019-04-19 hi </pre>
183 9541feb7 2019-04-08 git
184 9541feb7 2019-04-08 git
185 031e20a5 2019-04-19 hi ## Search for `pattern`, print the containing function (start with `def`) and line number
186 9541feb7 2019-04-08 git
187 031e20a5 2019-04-19 hi <pre>
188 031e20a5 2019-04-19 hi :g/<em>pattern</em>/?^ *<em>def</em> ?#
189 031e20a5 2019-04-19 hi </pre>
190 9541feb7 2019-04-08 git
191 9541feb7 2019-04-08 git
192 031e20a5 2019-04-19 hi ## Add &#35; to paragraph containing `pattern`
193 031e20a5 2019-04-19 hi
194 031e20a5 2019-04-19 hi <pre>
195 031e20a5 2019-04-19 hi :g/<em>pattern</em>/?^$?+,//-s/^/#
196 031e20a5 2019-04-19 hi </pre>
197 031e20a5 2019-04-19 hi
198 031e20a5 2019-04-19 hi
199 031e20a5 2019-04-19 hi ## Sort content of a multiline CSS block
200 031e20a5 2019-04-19 hi
201 9541feb7 2019-04-08 git :g/{$/+,/^}/-!sort
202 9541feb7 2019-04-08 git
203 9541feb7 2019-04-08 git
204 031e20a5 2019-04-19 hi ## Sort content of a multiline CSS block (media queries)
205 031e20a5 2019-04-19 hi
206 9541feb7 2019-04-08 git :g/^[^@].*{$/+,/}/-!sort
207 9541feb7 2019-04-08 git
208 9541feb7 2019-04-08 git
209 031e20a5 2019-04-19 hi ## Format content of `<p>` tag to fixed width
210 9541feb7 2019-04-08 git
211 031e20a5 2019-04-19 hi width = 40
212 bf5cacf5 2019-04-19 git
213 031e20a5 2019-04-19 hi <pre>
214 031e20a5 2019-04-19 hi :g/&lt;p&gt;/+,/&lt;\/p&gt;/-!fmt -<em>40</em>
215 031e20a5 2019-04-19 hi </pre>
216 031e20a5 2019-04-19 hi
217 031e20a5 2019-04-19 hi
218 c57b7323 2020-05-10 git ## Format whole document
219 c57b7323 2020-05-10 git
220 c57b7323 2020-05-10 git :%!fmt -s
221 c57b7323 2020-05-10 git
222 c57b7323 2020-05-10 git In your .nexrc
223 c57b7323 2020-05-10 git
224 c57b7323 2020-05-10 git <pre>
225 c57b7323 2020-05-10 git map gF :%!fmt -s<u>&lt;CTRL-V&gt;&lt;ENTER&gt;</u>
226 c57b7323 2020-05-10 git </pre>
227 c57b7323 2020-05-10 git
228 031e20a5 2019-04-19 hi ## Reverse all lines, move `m` all lines to 0
229 031e20a5 2019-04-19 hi
230 bf5cacf5 2019-04-19 git :g/1*/m0
231 bf5cacf5 2019-04-19 git
232 9541feb7 2019-04-08 git
233 031e20a5 2019-04-19 hi ## Swap `Lastname, Firstname` to `Firstname, Lastname`
234 031e20a5 2019-04-19 hi
235 0bb4466d 2019-04-08 git :%s/\(.*\), \(.*\)/\2 \1/
236 9541feb7 2019-04-08 git
237 8f839d09 2019-04-15 git
238 031e20a5 2019-04-19 hi ## Convert to lowercase
239 031e20a5 2019-04-19 hi
240 70b3c166 2019-04-20 hi :%s/.*/\L&/
241 8f839d09 2019-04-15 git
242 6c9b71bc 2019-04-06 git
243 64a200c4 2023-06-06 mischa ## Surround text with pattern
244 64a200c4 2023-06-06 mischa
245 64a200c4 2023-06-06 mischa :%s/.*/`pattern` & `pattern`/
246 64a200c4 2023-06-06 mischa
247 64a200c4 2023-06-06 mischa
248 031e20a5 2019-04-19 hi ## Join all lines
249 031e20a5 2019-04-19 hi
250 6c9b71bc 2019-04-06 git :%j
251 6c9b71bc 2019-04-06 git
252 031e20a5 2019-04-19 hi ## Copy `t` or move `m` lines containing `pattern`
253 9541feb7 2019-04-08 git
254 031e20a5 2019-04-19 hi <pre>
255 031e20a5 2019-04-19 hi :g/<em>pattern</em>/t$
256 031e20a5 2019-04-19 hi :g/<em>pattern</em>/m$
257 031e20a5 2019-04-19 hi </pre>
258 9541feb7 2019-04-08 git
259 031e20a5 2019-04-19 hi ## Select a column of a table
260 031e20a5 2019-04-19 hi Select 3rd column separated by colon (`:`)
261 6c9b71bc 2019-04-06 git
262 031e20a5 2019-04-19 hi <pre>
263 031e20a5 2019-04-19 hi :%!awk -F'<em>:</em>' '{print $<em>3</em>}'
264 031e20a5 2019-04-19 hi </pre>
265 6c9b71bc 2019-04-06 git
266 031e20a5 2019-04-19 hi ## Insert the sum of a list of numbers after an arbitrary number of lines
267 6c9b71bc 2019-04-06 git
268 70b3c166 2019-04-20 hi (1) mark the first line: `mk`
269 70b3c166 2019-04-20 hi (2) mark the last line: `ml`
270 9541feb7 2019-04-08 git
271 031e20a5 2019-04-19 hi <pre>
272 031e20a5 2019-04-19 hi :'k,'l!awk 'END{print "<em>total:</em>", i}{i+=$1; print}'
273 031e20a5 2019-04-19 hi </pre>
274 9541feb7 2019-04-08 git
275 031e20a5 2019-04-19 hi or
276 9541feb7 2019-04-08 git
277 031e20a5 2019-04-19 hi <pre>
278 031e20a5 2019-04-19 hi :'k,'l!awk 'END{print "<em>total:</em>", i} ++i || 1'
279 031e20a5 2019-04-19 hi </pre>
280 f8e3820c 2019-04-10 git
281 031e20a5 2019-04-19 hi ## Email the block
282 f8e3820c 2019-04-10 git
283 031e20a5 2019-04-19 hi <pre>
284 031e20a5 2019-04-19 hi :?^$?+,//-w !mail -s "<em>subject</em>" <em>email@example.com</em>
285 031e20a5 2019-04-19 hi </pre>
286 f8e3820c 2019-04-10 git
287 031e20a5 2019-04-19 hi ## Enable and use `ex` history
288 031e20a5 2019-04-19 hi
289 ade8cac0 2019-04-27 git (1) Set `ESC` key to enable history or add to `~/.nexrc`:
290 c2580c10 2019-04-20 hi
291 031e20a5 2019-04-19 hi <pre>
292 c2580c10 2019-04-20 hi :set cedit=<u>&lt;CTRL-V&gt;&lt;ESC&gt;</u>
293 c2580c10 2019-04-20 hi </pre>
294 031e20a5 2019-04-19 hi
295 c2580c10 2019-04-20 hi (2) Use it with:
296 c2580c10 2019-04-20 hi
297 c2580c10 2019-04-20 hi <pre>
298 031e20a5 2019-04-19 hi :<u>&lt;ESC&gt;</u>
299 ade8cac0 2019-04-27 git </pre>
300 ade8cac0 2019-04-27 git
301 ade8cac0 2019-04-27 git
302 ade8cac0 2019-04-27 git ## Integrate with tmux buffer
303 ade8cac0 2019-04-27 git
304 ade8cac0 2019-04-27 git (1) cut text from current position to mark 'm' into tmux buffer. Hit undo to put text back into vi buffer.
305 ade8cac0 2019-04-27 git
306 ade8cac0 2019-04-27 git <pre>
307 ade8cac0 2019-04-27 git !'mtmux load-buffer -
308 031e20a5 2019-04-19 hi </pre>
309 ade8cac0 2019-04-27 git
310 ade8cac0 2019-04-27 git (2) paste text from tmux buffer into vi buffer.
311 ade8cac0 2019-04-27 git
312 ade8cac0 2019-04-27 git <pre>
313 ade8cac0 2019-04-27 git :r!tmux show-buffer
314 ade8cac0 2019-04-27 git </pre>
315 ade8cac0 2019-04-27 git
316 ee74a164 2019-06-05 git (3) Map in ~/.nexrc (command mode)
317 ade8cac0 2019-04-27 git
318 ade8cac0 2019-04-27 git <pre>
319 ade8cac0 2019-04-27 git map gx !'mtmux load-buffer -<u>&lt;CTRL-V&gt;&lt;ENTER&gt;</u>
320 ade8cac0 2019-04-27 git map gy !'mtmux load-buffer -<u>&lt;CTRL-V&gt;&lt;ENTER&gt;</u>u
321 ade8cac0 2019-04-27 git map gp :r!tmux show-buffer<u>&lt;CTRL-V&gt;&lt;ENTER&gt;</u>
322 ade8cac0 2019-04-27 git </pre>
323 9e2dabb0 2019-04-27 git
324 9e2dabb0 2019-04-27 git
325 ee74a164 2019-06-05 git ## Remap ESC to ALT-i in ~/.nexrc (insert mode)
326 9e2dabb0 2019-04-27 git
327 9e2dabb0 2019-04-27 git <pre>
328 9e2dabb0 2019-04-27 git map! <u>&lt;CTRL-V&gt;&lt;ALT-i&gt;</u> <u>&lt;CTRL-V&gt;&lt;ESC&gt;</u>
329 9e2dabb0 2019-04-27 git </pre>
330 9e2dabb0 2019-04-27 git
331 9e2dabb0 2019-04-27 git