blob: da8ebd81e4e41e6933c7dd54e1bf89b5dda248ac [file] [log] [blame]
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001" Test for various Normal mode commands
2
Bram Moolenaara84a3dd2019-03-25 22:21:24 +01003source shared.vim
Bram Moolenaar5a4c3082019-12-01 15:23:11 +01004source check.vim
Bram Moolenaarca68ae12020-03-30 19:32:53 +02005source view_util.vim
Bram Moolenaar62aec932022-01-29 21:45:34 +00006import './vim9.vim' as v9
Bram Moolenaar7a1d3282022-06-16 13:04:45 +01007source screendump.vim
Bram Moolenaara84a3dd2019-03-25 22:21:24 +01008
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01009func Setup_NewWindow()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020010 10new
11 call setline(1, range(1,100))
12endfunc
13
Bram Moolenaar1bbb6192018-11-10 16:02:01 +010014func MyFormatExpr()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020015 " Adds '->$' at lines having numbers followed by trailing whitespace
16 for ln in range(v:lnum, v:lnum+v:count-1)
17 let line = getline(ln)
18 if getline(ln) =~# '\d\s\+$'
19 call setline(ln, substitute(line, '\s\+$', '', '') . '->$')
20 endif
21 endfor
Bram Moolenaar2931f2a2016-09-09 16:59:08 +020022endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020023
Bram Moolenaar1bbb6192018-11-10 16:02:01 +010024func CountSpaces(type, ...)
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020025 " for testing operatorfunc
26 " will count the number of spaces
27 " and return the result in g:a
28 let sel_save = &selection
29 let &selection = "inclusive"
30 let reg_save = @@
31
32 if a:0 " Invoked from Visual mode, use gv command.
33 silent exe "normal! gvy"
34 elseif a:type == 'line'
35 silent exe "normal! '[V']y"
36 else
37 silent exe "normal! `[v`]y"
38 endif
Bram Moolenaar777e7c22021-10-25 17:07:04 +010039 let g:a = strlen(substitute(@@, '[^ ]', '', 'g'))
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020040 let &selection = sel_save
41 let @@ = reg_save
Bram Moolenaar2931f2a2016-09-09 16:59:08 +020042endfunc
43
Bram Moolenaar1bbb6192018-11-10 16:02:01 +010044func OpfuncDummy(type, ...)
Bram Moolenaar4a08b0d2016-11-05 21:55:13 +010045 " for testing operatorfunc
Bram Moolenaar777e7c22021-10-25 17:07:04 +010046 let g:opt = &linebreak
Bram Moolenaar4a08b0d2016-11-05 21:55:13 +010047
48 if a:0 " Invoked from Visual mode, use gv command.
49 silent exe "normal! gvy"
50 elseif a:type == 'line'
51 silent exe "normal! '[V']y"
52 else
53 silent exe "normal! `[v`]y"
54 endif
55 " Create a new dummy window
56 new
Bram Moolenaar777e7c22021-10-25 17:07:04 +010057 let g:bufnr = bufnr('%')
Bram Moolenaar2931f2a2016-09-09 16:59:08 +020058endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020059
Bram Moolenaar1671f442020-03-10 07:48:13 +010060func Test_normal00_optrans()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020061 new
62 call append(0, ['1 This is a simple test: abcd', '2 This is the second line', '3 this is the third line'])
63 1
64 exe "norm! Sfoobar\<esc>"
65 call assert_equal(['foobar', '2 This is the second line', '3 this is the third line', ''], getline(1,'$'))
66 2
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020067 exe "norm! $vbsone"
68 call assert_equal(['foobar', '2 This is the second one', '3 this is the third line', ''], getline(1,'$'))
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020069 norm! VS Second line here
70 call assert_equal(['foobar', ' Second line here', '3 this is the third line', ''], getline(1, '$'))
71 %d
72 call append(0, ['4 This is a simple test: abcd', '5 This is the second line', '6 this is the third line'])
73 call append(0, ['1 This is a simple test: abcd', '2 This is the second line', '3 this is the third line'])
74
75 1
76 norm! 2D
77 call assert_equal(['3 this is the third line', '4 This is a simple test: abcd', '5 This is the second line', '6 this is the third line', ''], getline(1,'$'))
78 set cpo+=#
79 norm! 4D
80 call assert_equal(['', '4 This is a simple test: abcd', '5 This is the second line', '6 this is the third line', ''], getline(1,'$'))
81
82 " clean up
83 set cpo-=#
84 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +020085endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020086
Bram Moolenaar1bbb6192018-11-10 16:02:01 +010087func Test_normal01_keymodel()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020088 call Setup_NewWindow()
89 " Test 1: depending on 'keymodel' <s-down> does something different
Bram Moolenaar2931f2a2016-09-09 16:59:08 +020090 50
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020091 call feedkeys("V\<S-Up>y", 'tx')
92 call assert_equal(['47', '48', '49', '50'], getline("'<", "'>"))
Bram Moolenaar2931f2a2016-09-09 16:59:08 +020093 set keymodel=startsel
94 50
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020095 call feedkeys("V\<S-Up>y", 'tx')
96 call assert_equal(['49', '50'], getline("'<", "'>"))
97 " Start visual mode when keymodel = startsel
Bram Moolenaar2931f2a2016-09-09 16:59:08 +020098 50
Bram Moolenaar87bc3f72016-09-03 17:33:54 +020099 call feedkeys("\<S-Up>y", 'tx')
100 call assert_equal(['49', '5'], getreg(0, 0, 1))
Bram Moolenaar1671f442020-03-10 07:48:13 +0100101 " Use the different Shift special keys
102 50
103 call feedkeys("\<S-Right>\<S-Left>\<S-Up>\<S-Down>\<S-Home>\<S-End>y", 'tx')
104 call assert_equal(['50'], getline("'<", "'>"))
105 call assert_equal(['50', ''], getreg(0, 0, 1))
106
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200107 " Do not start visual mode when keymodel=
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200108 set keymodel=
109 50
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200110 call feedkeys("\<S-Up>y$", 'tx')
111 call assert_equal(['42'], getreg(0, 0, 1))
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200112 " Stop visual mode when keymodel=stopsel
113 set keymodel=stopsel
114 50
115 call feedkeys("Vkk\<Up>yy", 'tx')
116 call assert_equal(['47'], getreg(0, 0, 1))
117
118 set keymodel=
119 50
120 call feedkeys("Vkk\<Up>yy", 'tx')
121 call assert_equal(['47', '48', '49', '50'], getreg(0, 0, 1))
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200122
Bram Moolenaard7e5e942020-10-07 16:54:52 +0200123 " Test for using special keys to start visual selection
124 %d
125 call setline(1, ['red fox tail', 'red fox tail', 'red fox tail'])
126 set keymodel=startsel
127 " Test for <S-PageUp> and <S-PageDown>
128 call cursor(1, 1)
129 call feedkeys("\<S-PageDown>y", 'xt')
130 call assert_equal([0, 1, 1, 0], getpos("'<"))
131 call assert_equal([0, 3, 1, 0], getpos("'>"))
132 call feedkeys("Gz\<CR>8|\<S-PageUp>y", 'xt')
133 call assert_equal([0, 2, 1, 0], getpos("'<"))
134 call assert_equal([0, 3, 8, 0], getpos("'>"))
135 " Test for <S-C-Home> and <S-C-End>
136 call cursor(2, 12)
137 call feedkeys("\<S-C-Home>y", 'xt')
138 call assert_equal([0, 1, 1, 0], getpos("'<"))
139 call assert_equal([0, 2, 12, 0], getpos("'>"))
140 call cursor(1, 4)
141 call feedkeys("\<S-C-End>y", 'xt')
142 call assert_equal([0, 1, 4, 0], getpos("'<"))
143 call assert_equal([0, 3, 13, 0], getpos("'>"))
144 " Test for <S-C-Left> and <S-C-Right>
145 call cursor(2, 5)
146 call feedkeys("\<S-C-Right>y", 'xt')
147 call assert_equal([0, 2, 5, 0], getpos("'<"))
148 call assert_equal([0, 2, 9, 0], getpos("'>"))
149 call cursor(2, 9)
150 call feedkeys("\<S-C-Left>y", 'xt')
151 call assert_equal([0, 2, 5, 0], getpos("'<"))
152 call assert_equal([0, 2, 9, 0], getpos("'>"))
153
154 set keymodel&
155
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200156 " clean up
157 bw!
158endfunc
159
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100160func Test_normal03_join()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200161 " basic join test
162 call Setup_NewWindow()
163 50
164 norm! VJ
165 call assert_equal('50 51', getline('.'))
166 $
167 norm! J
168 call assert_equal('100', getline('.'))
169 $
170 norm! V9-gJ
171 call assert_equal('919293949596979899100', getline('.'))
172 call setline(1, range(1,100))
173 $
174 :j 10
175 call assert_equal('100', getline('.'))
Bram Moolenaar004a6782020-04-11 17:09:31 +0200176 call assert_beeps('normal GVJ')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200177 " clean up
178 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200179endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200180
Bram Moolenaar004a6782020-04-11 17:09:31 +0200181" basic filter test
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100182func Test_normal04_filter()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200183 " only test on non windows platform
Bram Moolenaar004a6782020-04-11 17:09:31 +0200184 CheckNotMSWindows
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200185 call Setup_NewWindow()
186 1
187 call feedkeys("!!sed -e 's/^/| /'\n", 'tx')
188 call assert_equal('| 1', getline('.'))
189 90
190 :sil :!echo one
191 call feedkeys('.', 'tx')
192 call assert_equal('| 90', getline('.'))
193 95
194 set cpo+=!
195 " 2 <CR>, 1: for executing the command,
196 " 2: clear hit-enter-prompt
197 call feedkeys("!!\n", 'tx')
198 call feedkeys(":!echo one\n\n", 'tx')
199 call feedkeys(".", 'tx')
200 call assert_equal('one', getline('.'))
201 set cpo-=!
202 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200203endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200204
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100205func Test_normal05_formatexpr()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200206 " basic formatexpr test
207 call Setup_NewWindow()
208 %d_
209 call setline(1, ['here: 1 ', '2', 'here: 3 ', '4', 'not here: '])
210 1
211 set formatexpr=MyFormatExpr()
212 norm! gqG
213 call assert_equal(['here: 1->$', '2', 'here: 3->$', '4', 'not here: '], getline(1,'$'))
214 set formatexpr=
215 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200216endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200217
Bram Moolenaard77f9d52016-09-04 15:13:39 +0200218func Test_normal05_formatexpr_newbuf()
219 " Edit another buffer in the 'formatexpr' function
220 new
221 func! Format()
222 edit another
223 endfunc
224 set formatexpr=Format()
225 norm gqG
226 bw!
227 set formatexpr=
228endfunc
229
230func Test_normal05_formatexpr_setopt()
231 " Change the 'formatexpr' value in the function
232 new
233 func! Format()
234 set formatexpr=
235 endfunc
236 set formatexpr=Format()
237 norm gqG
238 bw!
239 set formatexpr=
240endfunc
241
Bram Moolenaar2eaeaf32020-05-03 16:04:43 +0200242" When 'formatexpr' returns non-zero, internal formatting is used.
243func Test_normal_formatexpr_returns_nonzero()
244 new
245 call setline(1, ['one', 'two'])
246 func! Format()
247 return 1
248 endfunc
249 setlocal formatexpr=Format()
250 normal VGgq
251 call assert_equal(['one two'], getline(1, '$'))
252 setlocal formatexpr=
253 delfunc Format
254 close!
255endfunc
256
Yegappan Lakshmanan8bb65f22021-12-26 10:51:39 +0000257" Test for using a script-local function for 'formatexpr'
258func Test_formatexpr_scriptlocal_func()
259 func! s:Format()
260 let g:FormatArgs = [v:lnum, v:count]
261 endfunc
262 set formatexpr=s:Format()
263 call assert_equal(expand('<SID>') .. 'Format()', &formatexpr)
264 new | only
265 call setline(1, range(1, 40))
266 let g:FormatArgs = []
267 normal! 2GVjgq
268 call assert_equal([2, 2], g:FormatArgs)
269 bw!
270 set formatexpr=<SID>Format()
271 call assert_equal(expand('<SID>') .. 'Format()', &formatexpr)
272 new | only
273 call setline(1, range(1, 40))
274 let g:FormatArgs = []
275 normal! 4GVjgq
276 call assert_equal([4, 2], g:FormatArgs)
277 bw!
278 let &formatexpr = 's:Format()'
279 new | only
280 call setline(1, range(1, 40))
281 let g:FormatArgs = []
282 normal! 6GVjgq
283 call assert_equal([6, 2], g:FormatArgs)
284 bw!
285 let &formatexpr = '<SID>Format()'
286 new | only
287 call setline(1, range(1, 40))
288 let g:FormatArgs = []
289 normal! 8GVjgq
290 call assert_equal([8, 2], g:FormatArgs)
291 setlocal formatexpr=
292 delfunc s:Format
293 bw!
294endfunc
295
Bram Moolenaar004a6782020-04-11 17:09:31 +0200296" basic test for formatprg
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100297func Test_normal06_formatprg()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200298 " only test on non windows platform
Bram Moolenaar004a6782020-04-11 17:09:31 +0200299 CheckNotMSWindows
Bram Moolenaar9be7c042017-01-14 14:28:30 +0100300
301 " uses sed to number non-empty lines
Bram Moolenaarb152b6a2022-09-29 21:37:33 +0100302 call writefile(['#!/bin/sh', 'sed ''/./=''|sed ''/./{', 'N', 's/\n/ /', '}'''], 'Xsed_format.sh', 'D')
Bram Moolenaar9be7c042017-01-14 14:28:30 +0100303 call system('chmod +x ./Xsed_format.sh')
304 let text = ['a', '', 'c', '', ' ', 'd', 'e']
305 let expected = ['1 a', '', '3 c', '', '5 ', '6 d', '7 e']
306
307 10new
308 call setline(1, text)
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200309 set formatprg=./Xsed_format.sh
310 norm! gggqG
Bram Moolenaar9be7c042017-01-14 14:28:30 +0100311 call assert_equal(expected, getline(1, '$'))
Bram Moolenaar004a6782020-04-11 17:09:31 +0200312 %d
Bram Moolenaar9be7c042017-01-14 14:28:30 +0100313
Bram Moolenaar9be7c042017-01-14 14:28:30 +0100314 call setline(1, text)
315 set formatprg=donothing
316 setlocal formatprg=./Xsed_format.sh
317 norm! gggqG
318 call assert_equal(expected, getline(1, '$'))
Bram Moolenaar004a6782020-04-11 17:09:31 +0200319 %d
Bram Moolenaar9be7c042017-01-14 14:28:30 +0100320
Bram Moolenaar004a6782020-04-11 17:09:31 +0200321 " Check for the command-line ranges added to 'formatprg'
322 set formatprg=cat
323 call setline(1, ['one', 'two', 'three', 'four', 'five'])
324 call feedkeys('gggqG', 'xt')
325 call assert_equal('.,$!cat', @:)
326 call feedkeys('2Ggq2j', 'xt')
327 call assert_equal('.,.+2!cat', @:)
328
329 bw!
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200330 " clean up
331 set formatprg=
Bram Moolenaar9be7c042017-01-14 14:28:30 +0100332 setlocal formatprg=
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200333endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200334
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100335func Test_normal07_internalfmt()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200336 " basic test for internal formmatter to textwidth of 12
337 let list=range(1,11)
338 call map(list, 'v:val." "')
339 10new
340 call setline(1, list)
341 set tw=12
Bram Moolenaar004a6782020-04-11 17:09:31 +0200342 norm! ggVGgq
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200343 call assert_equal(['1 2 3', '4 5 6', '7 8 9', '10 11 '], getline(1, '$'))
344 " clean up
Bram Moolenaar9be7c042017-01-14 14:28:30 +0100345 set tw=0
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200346 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200347endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200348
Bram Moolenaar004a6782020-04-11 17:09:31 +0200349" basic tests for foldopen/folddelete
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100350func Test_normal08_fold()
Bram Moolenaar004a6782020-04-11 17:09:31 +0200351 CheckFeature folding
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200352 call Setup_NewWindow()
353 50
354 setl foldenable fdm=marker
355 " First fold
356 norm! V4jzf
357 " check that folds have been created
358 call assert_equal(['50/*{{{*/', '51', '52', '53', '54/*}}}*/'], getline(50,54))
359 " Second fold
360 46
361 norm! V10jzf
362 " check that folds have been created
363 call assert_equal('46/*{{{*/', getline(46))
364 call assert_equal('60/*}}}*/', getline(60))
365 norm! k
366 call assert_equal('45', getline('.'))
367 norm! j
368 call assert_equal('46/*{{{*/', getline('.'))
369 norm! j
370 call assert_equal('61', getline('.'))
371 norm! k
372 " open a fold
373 norm! Vzo
374 norm! k
375 call assert_equal('45', getline('.'))
376 norm! j
377 call assert_equal('46/*{{{*/', getline('.'))
378 norm! j
379 call assert_equal('47', getline('.'))
380 norm! k
381 norm! zcVzO
382 call assert_equal('46/*{{{*/', getline('.'))
383 norm! j
384 call assert_equal('47', getline('.'))
385 norm! j
386 call assert_equal('48', getline('.'))
387 norm! j
388 call assert_equal('49', getline('.'))
389 norm! j
390 call assert_equal('50/*{{{*/', getline('.'))
391 norm! j
392 call assert_equal('51', getline('.'))
393 " delete folds
394 :46
395 " collapse fold
396 norm! V14jzC
397 " delete all folds recursively
398 norm! VzD
399 call assert_equal(['46', '47', '48', '49', '50', '51', '52', '53', '54', '55', '56', '57', '58', '59', '60'], getline(46,60))
400
401 " clean up
402 setl nofoldenable fdm=marker
403 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200404endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200405
Bram Moolenaar2228cd72021-11-22 14:16:08 +0000406func Test_normal09a_operatorfunc()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200407 " Test operatorfunc
408 call Setup_NewWindow()
409 " Add some spaces for counting
410 50,60s/$/ /
411 unlet! g:a
412 let g:a=0
413 nmap <buffer><silent> ,, :set opfunc=CountSpaces<CR>g@
414 vmap <buffer><silent> ,, :<C-U>call CountSpaces(visualmode(), 1)<CR>
415 50
416 norm V2j,,
417 call assert_equal(6, g:a)
418 norm V,,
419 call assert_equal(2, g:a)
420 norm ,,l
421 call assert_equal(0, g:a)
422 50
423 exe "norm 0\<c-v>10j2l,,"
424 call assert_equal(11, g:a)
425 50
426 norm V10j,,
427 call assert_equal(22, g:a)
428
429 " clean up
430 unmap <buffer> ,,
431 set opfunc=
Bram Moolenaar4a08b0d2016-11-05 21:55:13 +0100432 unlet! g:a
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200433 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200434endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200435
Bram Moolenaar2228cd72021-11-22 14:16:08 +0000436func Test_normal09b_operatorfunc()
Bram Moolenaar4a08b0d2016-11-05 21:55:13 +0100437 " Test operatorfunc
438 call Setup_NewWindow()
439 " Add some spaces for counting
440 50,60s/$/ /
441 unlet! g:opt
442 set linebreak
443 nmap <buffer><silent> ,, :set opfunc=OpfuncDummy<CR>g@
444 50
445 norm ,,j
446 exe "bd!" g:bufnr
447 call assert_true(&linebreak)
448 call assert_equal(g:opt, &linebreak)
449 set nolinebreak
450 norm ,,j
451 exe "bd!" g:bufnr
452 call assert_false(&linebreak)
453 call assert_equal(g:opt, &linebreak)
454
455 " clean up
456 unmap <buffer> ,,
457 set opfunc=
Bram Moolenaaree4e0c12020-04-06 21:35:05 +0200458 call assert_fails('normal Vg@', 'E774:')
Bram Moolenaar4a08b0d2016-11-05 21:55:13 +0100459 bw!
460 unlet! g:opt
461endfunc
462
Bram Moolenaar2228cd72021-11-22 14:16:08 +0000463func OperatorfuncRedo(_)
464 let g:opfunc_count = v:count
465endfunc
466
Bram Moolenaarb3bd1d32022-01-02 13:05:45 +0000467func Underscorize(_)
468 normal! '[V']r_
469endfunc
470
Bram Moolenaar2228cd72021-11-22 14:16:08 +0000471func Test_normal09c_operatorfunc()
472 " Test redoing operatorfunc
473 new
474 call setline(1, 'some text')
475 set operatorfunc=OperatorfuncRedo
476 normal v3g@
477 call assert_equal(3, g:opfunc_count)
478 let g:opfunc_count = 0
479 normal .
480 call assert_equal(3, g:opfunc_count)
481
482 bw!
483 unlet g:opfunc_count
Bram Moolenaarb3bd1d32022-01-02 13:05:45 +0000484
485 " Test redoing Visual mode
486 set operatorfunc=Underscorize
487 new
488 call setline(1, ['first', 'first', 'third', 'third', 'second'])
naohiro ono5c75eed2022-01-03 11:15:47 +0000489 normal! 1GVjg@
Bram Moolenaarb3bd1d32022-01-02 13:05:45 +0000490 normal! 5G.
491 normal! 3G.
492 call assert_equal(['_____', '_____', '_____', '_____', '______'], getline(1, '$'))
493 bwipe!
Bram Moolenaar2228cd72021-11-22 14:16:08 +0000494 set operatorfunc=
495endfunc
496
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000497" Test for different ways of setting the 'operatorfunc' option
498func Test_opfunc_callback()
499 new
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000500 func OpFunc1(callnr, type)
501 let g:OpFunc1Args = [a:callnr, a:type]
502 endfunc
503 func OpFunc2(type)
504 let g:OpFunc2Args = [a:type]
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000505 endfunc
506
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000507 let lines =<< trim END
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000508 #" Test for using a function name
509 LET &opfunc = 'g:OpFunc2'
510 LET g:OpFunc2Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000511 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000512 call assert_equal(['char'], g:OpFunc2Args)
513
514 #" Test for using a function()
515 set opfunc=function('g:OpFunc1',\ [10])
516 LET g:OpFunc1Args = []
517 normal! g@l
518 call assert_equal([10, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000519
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000520 #" Using a funcref variable to set 'operatorfunc'
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000521 VAR Fn = function('g:OpFunc1', [11])
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000522 LET &opfunc = Fn
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000523 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000524 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000525 call assert_equal([11, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000526
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000527 #" Using a string(funcref_variable) to set 'operatorfunc'
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000528 LET Fn = function('g:OpFunc1', [12])
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000529 LET &operatorfunc = string(Fn)
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000530 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000531 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000532 call assert_equal([12, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000533
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000534 #" Test for using a funcref()
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000535 set operatorfunc=funcref('g:OpFunc1',\ [13])
536 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000537 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000538 call assert_equal([13, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000539
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000540 #" Using a funcref variable to set 'operatorfunc'
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000541 LET Fn = funcref('g:OpFunc1', [14])
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000542 LET &opfunc = Fn
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000543 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000544 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000545 call assert_equal([14, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000546
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000547 #" Using a string(funcref_variable) to set 'operatorfunc'
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000548 LET Fn = funcref('g:OpFunc1', [15])
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000549 LET &opfunc = string(Fn)
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000550 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000551 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000552 call assert_equal([15, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000553
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000554 #" Test for using a lambda function using set
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000555 VAR optval = "LSTART a LMIDDLE OpFunc1(16, a) LEND"
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000556 LET optval = substitute(optval, ' ', '\\ ', 'g')
557 exe "set opfunc=" .. optval
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000558 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000559 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000560 call assert_equal([16, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000561
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000562 #" Test for using a lambda function using LET
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000563 LET &opfunc = LSTART a LMIDDLE OpFunc1(17, a) LEND
564 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000565 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000566 call assert_equal([17, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000567
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000568 #" Set 'operatorfunc' to a string(lambda expression)
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000569 LET &opfunc = 'LSTART a LMIDDLE OpFunc1(18, a) LEND'
570 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000571 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000572 call assert_equal([18, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000573
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000574 #" Set 'operatorfunc' to a variable with a lambda expression
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000575 VAR Lambda = LSTART a LMIDDLE OpFunc1(19, a) LEND
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000576 LET &opfunc = Lambda
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000577 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000578 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000579 call assert_equal([19, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000580
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000581 #" Set 'operatorfunc' to a string(variable with a lambda expression)
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000582 LET Lambda = LSTART a LMIDDLE OpFunc1(20, a) LEND
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000583 LET &opfunc = string(Lambda)
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000584 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000585 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000586 call assert_equal([20, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000587
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000588 #" Try to use 'operatorfunc' after the function is deleted
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000589 func g:TmpOpFunc1(type)
590 let g:TmpOpFunc1Args = [21, a:type]
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000591 endfunc
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000592 LET &opfunc = function('g:TmpOpFunc1')
593 delfunc g:TmpOpFunc1
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000594 call test_garbagecollect_now()
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000595 LET g:TmpOpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000596 call assert_fails('normal! g@l', 'E117:')
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000597 call assert_equal([], g:TmpOpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000598
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000599 #" Try to use a function with two arguments for 'operatorfunc'
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000600 func g:TmpOpFunc2(x, y)
601 let g:TmpOpFunc2Args = [a:x, a:y]
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000602 endfunc
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000603 set opfunc=TmpOpFunc2
604 LET g:TmpOpFunc2Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000605 call assert_fails('normal! g@l', 'E119:')
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000606 call assert_equal([], g:TmpOpFunc2Args)
607 delfunc TmpOpFunc2
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000608
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000609 #" Try to use a lambda function with two arguments for 'operatorfunc'
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000610 LET &opfunc = LSTART a, b LMIDDLE OpFunc1(22, b) LEND
611 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000612 call assert_fails('normal! g@l', 'E119:')
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000613 call assert_equal([], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000614
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000615 #" Test for clearing the 'operatorfunc' option
616 set opfunc=''
617 set opfunc&
618 call assert_fails("set opfunc=function('abc')", "E700:")
619 call assert_fails("set opfunc=funcref('abc')", "E700:")
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000620
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000621 #" set 'operatorfunc' to a non-existing function
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000622 LET &opfunc = function('g:OpFunc1', [23])
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000623 call assert_fails("set opfunc=function('NonExistingFunc')", 'E700:')
624 call assert_fails("LET &opfunc = function('NonExistingFunc')", 'E700:')
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000625 LET g:OpFunc1Args = []
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000626 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000627 call assert_equal([23, 'char'], g:OpFunc1Args)
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000628 END
Bram Moolenaar62aec932022-01-29 21:45:34 +0000629 call v9.CheckTransLegacySuccess(lines)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000630
Yegappan Lakshmanandb1a4102021-12-17 16:21:20 +0000631 " Test for using a script-local function name
632 func s:OpFunc3(type)
633 let g:OpFunc3Args = [a:type]
634 endfunc
635 set opfunc=s:OpFunc3
636 let g:OpFunc3Args = []
637 normal! g@l
638 call assert_equal(['char'], g:OpFunc3Args)
639
640 let &opfunc = 's:OpFunc3'
641 let g:OpFunc3Args = []
642 normal! g@l
643 call assert_equal(['char'], g:OpFunc3Args)
644 delfunc s:OpFunc3
645
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000646 " Using Vim9 lambda expression in legacy context should fail
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000647 set opfunc=(a)\ =>\ OpFunc1(24,\ a)
648 let g:OpFunc1Args = []
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000649 call assert_fails('normal! g@l', 'E117:')
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000650 call assert_equal([], g:OpFunc1Args)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000651
Yegappan Lakshmanan6ae8fae2021-12-12 16:26:44 +0000652 " set 'operatorfunc' to a partial with dict. This used to cause a crash.
653 func SetOpFunc()
654 let operator = {'execute': function('OperatorExecute')}
655 let &opfunc = operator.execute
656 endfunc
657 func OperatorExecute(_) dict
658 endfunc
659 call SetOpFunc()
660 call test_garbagecollect_now()
661 set operatorfunc=
662 delfunc SetOpFunc
663 delfunc OperatorExecute
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000664
665 " Vim9 tests
666 let lines =<< trim END
667 vim9script
668
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000669 def g:Vim9opFunc(val: number, type: string): void
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000670 g:OpFunc1Args = [val, type]
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000671 enddef
Yegappan Lakshmanandb1a4102021-12-17 16:21:20 +0000672
673 # Test for using a def function with opfunc
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000674 set opfunc=function('g:Vim9opFunc',\ [60])
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000675 g:OpFunc1Args = []
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000676 normal! g@l
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000677 assert_equal([60, 'char'], g:OpFunc1Args)
Yegappan Lakshmanandb1a4102021-12-17 16:21:20 +0000678
679 # Test for using a global function name
680 &opfunc = g:OpFunc2
681 g:OpFunc2Args = []
682 normal! g@l
683 assert_equal(['char'], g:OpFunc2Args)
684 bw!
685
686 # Test for using a script-local function name
Bram Moolenaar62b191c2022-02-12 20:34:50 +0000687 def LocalOpFunc(type: string): void
Yegappan Lakshmanandb1a4102021-12-17 16:21:20 +0000688 g:LocalOpFuncArgs = [type]
689 enddef
Bram Moolenaar62b191c2022-02-12 20:34:50 +0000690 &opfunc = LocalOpFunc
Yegappan Lakshmanandb1a4102021-12-17 16:21:20 +0000691 g:LocalOpFuncArgs = []
692 normal! g@l
693 assert_equal(['char'], g:LocalOpFuncArgs)
694 bw!
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000695 END
Bram Moolenaar62aec932022-01-29 21:45:34 +0000696 call v9.CheckScriptSuccess(lines)
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000697
Yegappan Lakshmanane7f4abd2021-12-24 20:47:38 +0000698 " setting 'opfunc' to a script local function outside of a script context
699 " should fail
700 let cleanup =<< trim END
701 call writefile([execute('messages')], 'Xtest.out')
702 qall
703 END
Bram Moolenaarb152b6a2022-09-29 21:37:33 +0100704 call writefile(cleanup, 'Xverify.vim', 'D')
Yegappan Lakshmanane7f4abd2021-12-24 20:47:38 +0000705 call RunVim([], [], "-c \"set opfunc=s:abc\" -S Xverify.vim")
706 call assert_match('E81: Using <SID> not in a', readfile('Xtest.out')[0])
707 call delete('Xtest.out')
Yegappan Lakshmanane7f4abd2021-12-24 20:47:38 +0000708
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000709 " cleanup
710 set opfunc&
Yegappan Lakshmanan04ef1fb2021-12-12 20:08:05 +0000711 delfunc OpFunc1
712 delfunc OpFunc2
713 unlet g:OpFunc1Args g:OpFunc2Args
Yegappan Lakshmanan2172bff2021-12-08 10:46:21 +0000714 %bw!
715endfunc
716
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100717func Test_normal10_expand()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200718 " Test for expand()
719 10new
720 call setline(1, ['1', 'ifooar,,cbar'])
721 2
722 norm! $
Bram Moolenaar65f08472017-09-10 18:16:20 +0200723 call assert_equal('cbar', expand('<cword>'))
724 call assert_equal('ifooar,,cbar', expand('<cWORD>'))
725
726 call setline(1, ['prx = list[idx];'])
727 1
728 let expected = ['', 'prx', 'prx', 'prx',
729 \ 'list', 'list', 'list', 'list', 'list', 'list', 'list',
730 \ 'idx', 'idx', 'idx', 'idx',
731 \ 'list[idx]',
732 \ '];',
733 \ ]
734 for i in range(1, 16)
735 exe 'norm ' . i . '|'
736 call assert_equal(expected[i], expand('<cexpr>'), 'i == ' . i)
737 endfor
738
Bram Moolenaard7e5e942020-10-07 16:54:52 +0200739 " Test for <cexpr> in state.val and ptr->val
740 call setline(1, 'x = state.val;')
741 call cursor(1, 10)
742 call assert_equal('state.val', expand('<cexpr>'))
743 call setline(1, 'x = ptr->val;')
744 call cursor(1, 9)
745 call assert_equal('ptr->val', expand('<cexpr>'))
746
Bram Moolenaarae6f8652017-12-20 22:32:20 +0100747 if executable('echo')
748 " Test expand(`...`) i.e. backticks command expansion.
Bram Moolenaar077ff432019-10-28 00:42:21 +0100749 call assert_equal('abcde', expand('`echo abcde`'))
Bram Moolenaarae6f8652017-12-20 22:32:20 +0100750 endif
751
752 " Test expand(`=...`) i.e. backticks expression expansion
753 call assert_equal('5', expand('`=2+3`'))
Bram Moolenaar8b633132020-03-20 18:20:51 +0100754 call assert_equal('3.14', expand('`=3.14`'))
Bram Moolenaarae6f8652017-12-20 22:32:20 +0100755
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200756 " clean up
757 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200758endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200759
Bram Moolenaard7e5e942020-10-07 16:54:52 +0200760" Test for expand() in latin1 encoding
761func Test_normal_expand_latin1()
762 new
763 let save_enc = &encoding
764 set encoding=latin1
765 call setline(1, 'val = item->color;')
766 call cursor(1, 11)
767 call assert_equal('color', expand("<cword>"))
768 call assert_equal('item->color', expand("<cexpr>"))
769 let &encoding = save_enc
770 bw!
771endfunc
772
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100773func Test_normal11_showcmd()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200774 " test for 'showcmd'
775 10new
776 exe "norm! ofoobar\<esc>"
777 call assert_equal(2, line('$'))
778 set showcmd
779 exe "norm! ofoobar2\<esc>"
780 call assert_equal(3, line('$'))
781 exe "norm! VAfoobar3\<esc>"
782 call assert_equal(3, line('$'))
783 exe "norm! 0d3\<del>2l"
784 call assert_equal('obar2foobar3', getline('.'))
Bram Moolenaard1ad99b2020-10-04 16:16:54 +0200785 " test for the visual block size displayed in the status line
786 call setline(1, ['aaaaa', 'bbbbb', 'ccccc'])
787 call feedkeys("ggl\<C-V>lljj", 'xt')
788 redraw!
789 call assert_match('3x3$', Screenline(&lines))
790 call feedkeys("\<C-V>", 'xt')
791 " test for visually selecting a multi-byte character
792 call setline(1, ["\U2206"])
793 call feedkeys("ggv", 'xt')
794 redraw!
795 call assert_match('1-3$', Screenline(&lines))
796 call feedkeys("v", 'xt')
Bram Moolenaard7e5e942020-10-07 16:54:52 +0200797 " test for visually selecting the end of line
798 call setline(1, ["foobar"])
799 call feedkeys("$vl", 'xt')
800 redraw!
801 call assert_match('2$', Screenline(&lines))
802 call feedkeys("y", 'xt')
803 call assert_equal("r\n", @")
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200804 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200805endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200806
Bram Moolenaar1671f442020-03-10 07:48:13 +0100807" Test for nv_error and normal command errors
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100808func Test_normal12_nv_error()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200809 10new
810 call setline(1, range(1,5))
811 " should not do anything, just beep
Bram Moolenaarf5f1e102020-03-08 05:13:15 +0100812 call assert_beeps('exe "norm! <c-k>"')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200813 call assert_equal(map(range(1,5), 'string(v:val)'), getline(1,'$'))
Bram Moolenaarf5f1e102020-03-08 05:13:15 +0100814 call assert_beeps('normal! G2dd')
815 call assert_beeps("normal! g\<C-A>")
816 call assert_beeps("normal! g\<C-X>")
817 call assert_beeps("normal! g\<C-B>")
Bram Moolenaar1671f442020-03-10 07:48:13 +0100818 call assert_beeps("normal! vQ\<Esc>")
819 call assert_beeps("normal! 2[[")
820 call assert_beeps("normal! 2]]")
821 call assert_beeps("normal! 2[]")
822 call assert_beeps("normal! 2][")
823 call assert_beeps("normal! 4[z")
824 call assert_beeps("normal! 4]z")
825 call assert_beeps("normal! 4[c")
826 call assert_beeps("normal! 4]c")
827 call assert_beeps("normal! 200%")
828 call assert_beeps("normal! %")
829 call assert_beeps("normal! 2{")
830 call assert_beeps("normal! 2}")
831 call assert_beeps("normal! r\<Right>")
832 call assert_beeps("normal! 8ry")
833 call assert_beeps('normal! "@')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200834 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200835endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200836
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100837func Test_normal13_help()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200838 " Test for F1
839 call assert_equal(1, winnr())
840 call feedkeys("\<f1>", 'txi')
841 call assert_match('help\.txt', bufname('%'))
842 call assert_equal(2, winnr('$'))
843 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200844endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200845
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100846func Test_normal14_page()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200847 " basic test for Ctrl-F and Ctrl-B
848 call Setup_NewWindow()
849 exe "norm! \<c-f>"
850 call assert_equal('9', getline('.'))
851 exe "norm! 2\<c-f>"
852 call assert_equal('25', getline('.'))
853 exe "norm! 2\<c-b>"
854 call assert_equal('18', getline('.'))
855 1
856 set scrolloff=5
857 exe "norm! 2\<c-f>"
858 call assert_equal('21', getline('.'))
859 exe "norm! \<c-b>"
860 call assert_equal('13', getline('.'))
861 1
862 set scrolloff=99
863 exe "norm! \<c-f>"
864 call assert_equal('13', getline('.'))
865 set scrolloff=0
866 100
867 exe "norm! $\<c-b>"
868 call assert_equal('92', getline('.'))
869 call assert_equal([0, 92, 1, 0, 1], getcurpos())
870 100
871 set nostartofline
872 exe "norm! $\<c-b>"
873 call assert_equal('92', getline('.'))
naohiro ono56200ee2022-01-01 14:59:44 +0000874 call assert_equal([0, 92, 2, 0, v:maxcol], getcurpos())
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200875 " cleanup
876 set startofline
877 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +0200878endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200879
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100880func Test_normal14_page_eol()
Bram Moolenaarbc54f3f2016-09-04 14:34:28 +0200881 10new
882 norm oxxxxxxx
883 exe "norm 2\<c-f>"
884 " check with valgrind that cursor is put back in column 1
885 exe "norm 2\<c-b>"
886 bw!
887endfunc
888
Bram Moolenaar1671f442020-03-10 07:48:13 +0100889" Test for errors with z command
890func Test_normal_z_error()
891 call assert_beeps('normal! z2p')
Christian Brabandt2fa93842021-05-30 22:17:25 +0200892 call assert_beeps('normal! zq')
Yegappan Lakshmananb0ad2d92022-01-27 13:16:59 +0000893 call assert_beeps('normal! cz1')
Bram Moolenaar1671f442020-03-10 07:48:13 +0100894endfunc
895
Bram Moolenaar1bbb6192018-11-10 16:02:01 +0100896func Test_normal15_z_scroll_vert()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200897 " basic test for z commands that scroll the window
898 call Setup_NewWindow()
899 100
900 norm! >>
901 " Test for z<cr>
902 exe "norm! z\<cr>"
903 call assert_equal(' 100', getline('.'))
904 call assert_equal(100, winsaveview()['topline'])
905 call assert_equal([0, 100, 2, 0, 9], getcurpos())
906
907 " Test for zt
908 21
909 norm! >>0zt
910 call assert_equal(' 21', getline('.'))
911 call assert_equal(21, winsaveview()['topline'])
912 call assert_equal([0, 21, 1, 0, 8], getcurpos())
913
914 " Test for zb
915 30
916 norm! >>$ztzb
917 call assert_equal(' 30', getline('.'))
918 call assert_equal(30, winsaveview()['topline']+winheight(0)-1)
naohiro ono56200ee2022-01-01 14:59:44 +0000919 call assert_equal([0, 30, 3, 0, v:maxcol], getcurpos())
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200920
921 " Test for z-
922 1
923 30
924 norm! 0z-
925 call assert_equal(' 30', getline('.'))
926 call assert_equal(30, winsaveview()['topline']+winheight(0)-1)
927 call assert_equal([0, 30, 2, 0, 9], getcurpos())
928
929 " Test for z{height}<cr>
930 call assert_equal(10, winheight(0))
931 exe "norm! z12\<cr>"
932 call assert_equal(12, winheight(0))
Yegappan Lakshmananb0ad2d92022-01-27 13:16:59 +0000933 exe "norm! z15\<Del>0\<cr>"
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200934 call assert_equal(10, winheight(0))
935
936 " Test for z.
937 1
938 21
939 norm! 0z.
940 call assert_equal(' 21', getline('.'))
941 call assert_equal(17, winsaveview()['topline'])
942 call assert_equal([0, 21, 2, 0, 9], getcurpos())
943
944 " Test for zz
945 1
946 21
947 norm! 0zz
948 call assert_equal(' 21', getline('.'))
949 call assert_equal(17, winsaveview()['topline'])
950 call assert_equal([0, 21, 1, 0, 8], getcurpos())
951
952 " Test for z+
953 11
954 norm! zt
955 norm! z+
956 call assert_equal(' 21', getline('.'))
957 call assert_equal(21, winsaveview()['topline'])
958 call assert_equal([0, 21, 2, 0, 9], getcurpos())
959
960 " Test for [count]z+
961 1
962 norm! 21z+
963 call assert_equal(' 21', getline('.'))
964 call assert_equal(21, winsaveview()['topline'])
965 call assert_equal([0, 21, 2, 0, 9], getcurpos())
966
Bram Moolenaar8a9bc952020-10-02 18:48:07 +0200967 " Test for z+ with [count] greater than buffer size
968 1
969 norm! 1000z+
970 call assert_equal(' 100', getline('.'))
971 call assert_equal(100, winsaveview()['topline'])
972 call assert_equal([0, 100, 2, 0, 9], getcurpos())
973
974 " Test for z+ from the last buffer line
975 norm! Gz.z+
976 call assert_equal(' 100', getline('.'))
977 call assert_equal(100, winsaveview()['topline'])
978 call assert_equal([0, 100, 2, 0, 9], getcurpos())
979
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200980 " Test for z^
981 norm! 22z+0
982 norm! z^
983 call assert_equal(' 21', getline('.'))
984 call assert_equal(12, winsaveview()['topline'])
985 call assert_equal([0, 21, 2, 0, 9], getcurpos())
986
Bram Moolenaar8a9bc952020-10-02 18:48:07 +0200987 " Test for z^ from first buffer line
988 norm! ggz^
989 call assert_equal('1', getline('.'))
990 call assert_equal(1, winsaveview()['topline'])
991 call assert_equal([0, 1, 1, 0, 1], getcurpos())
992
Bram Moolenaar87bc3f72016-09-03 17:33:54 +0200993 " Test for [count]z^
994 1
995 norm! 30z^
996 call assert_equal(' 21', getline('.'))
997 call assert_equal(12, winsaveview()['topline'])
998 call assert_equal([0, 21, 2, 0, 9], getcurpos())
999
1000 " cleanup
1001 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001002endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001003
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001004func Test_normal16_z_scroll_hor()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001005 " basic test for z commands that scroll the window
1006 10new
1007 15vsp
1008 set nowrap listchars=
1009 let lineA='abcdefghijklmnopqrstuvwxyz'
1010 let lineB='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'
1011 $put =lineA
1012 $put =lineB
1013 1d
1014
Bram Moolenaar1671f442020-03-10 07:48:13 +01001015 " Test for zl and zh with a count
1016 norm! 0z10l
1017 call assert_equal([11, 1], [col('.'), wincol()])
1018 norm! z4h
1019 call assert_equal([11, 5], [col('.'), wincol()])
1020 normal! 2gg
1021
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001022 " Test for zl
1023 1
1024 norm! 5zl
1025 call assert_equal(lineA, getline('.'))
1026 call assert_equal(6, col('.'))
1027 call assert_equal(5, winsaveview()['leftcol'])
1028 norm! yl
1029 call assert_equal('f', @0)
1030
1031 " Test for zh
1032 norm! 2zh
1033 call assert_equal(lineA, getline('.'))
1034 call assert_equal(6, col('.'))
1035 norm! yl
1036 call assert_equal('f', @0)
1037 call assert_equal(3, winsaveview()['leftcol'])
1038
1039 " Test for zL
1040 norm! zL
1041 call assert_equal(11, col('.'))
1042 norm! yl
1043 call assert_equal('k', @0)
1044 call assert_equal(10, winsaveview()['leftcol'])
1045 norm! 2zL
1046 call assert_equal(25, col('.'))
1047 norm! yl
1048 call assert_equal('y', @0)
1049 call assert_equal(24, winsaveview()['leftcol'])
1050
1051 " Test for zH
1052 norm! 2zH
1053 call assert_equal(25, col('.'))
1054 call assert_equal(10, winsaveview()['leftcol'])
1055 norm! yl
1056 call assert_equal('y', @0)
1057
1058 " Test for zs
1059 norm! $zs
1060 call assert_equal(26, col('.'))
1061 call assert_equal(25, winsaveview()['leftcol'])
1062 norm! yl
1063 call assert_equal('z', @0)
1064
1065 " Test for ze
1066 norm! ze
1067 call assert_equal(26, col('.'))
1068 call assert_equal(11, winsaveview()['leftcol'])
1069 norm! yl
1070 call assert_equal('z', @0)
1071
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02001072 " Test for zs and ze with folds
1073 %fold
1074 norm! $zs
1075 call assert_equal(26, col('.'))
1076 call assert_equal(0, winsaveview()['leftcol'])
1077 norm! yl
1078 call assert_equal('z', @0)
1079 norm! ze
1080 call assert_equal(26, col('.'))
1081 call assert_equal(0, winsaveview()['leftcol'])
1082 norm! yl
1083 call assert_equal('z', @0)
1084
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001085 " cleanup
1086 set wrap listchars=eol:$
1087 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001088endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001089
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001090func Test_normal17_z_scroll_hor2()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001091 " basic test for z commands that scroll the window
1092 " using 'sidescrolloff' setting
1093 10new
1094 20vsp
1095 set nowrap listchars= sidescrolloff=5
1096 let lineA='abcdefghijklmnopqrstuvwxyz'
1097 let lineB='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'
1098 $put =lineA
1099 $put =lineB
1100 1d
1101
1102 " Test for zl
1103 1
1104 norm! 5zl
1105 call assert_equal(lineA, getline('.'))
1106 call assert_equal(11, col('.'))
1107 call assert_equal(5, winsaveview()['leftcol'])
1108 norm! yl
1109 call assert_equal('k', @0)
1110
1111 " Test for zh
1112 norm! 2zh
1113 call assert_equal(lineA, getline('.'))
1114 call assert_equal(11, col('.'))
1115 norm! yl
1116 call assert_equal('k', @0)
1117 call assert_equal(3, winsaveview()['leftcol'])
1118
1119 " Test for zL
1120 norm! 0zL
1121 call assert_equal(16, col('.'))
1122 norm! yl
1123 call assert_equal('p', @0)
1124 call assert_equal(10, winsaveview()['leftcol'])
1125 norm! 2zL
1126 call assert_equal(26, col('.'))
1127 norm! yl
1128 call assert_equal('z', @0)
1129 call assert_equal(15, winsaveview()['leftcol'])
1130
1131 " Test for zH
1132 norm! 2zH
1133 call assert_equal(15, col('.'))
1134 call assert_equal(0, winsaveview()['leftcol'])
1135 norm! yl
1136 call assert_equal('o', @0)
1137
1138 " Test for zs
1139 norm! $zs
1140 call assert_equal(26, col('.'))
1141 call assert_equal(20, winsaveview()['leftcol'])
1142 norm! yl
1143 call assert_equal('z', @0)
1144
1145 " Test for ze
1146 norm! ze
1147 call assert_equal(26, col('.'))
1148 call assert_equal(11, winsaveview()['leftcol'])
1149 norm! yl
1150 call assert_equal('z', @0)
1151
1152 " cleanup
1153 set wrap listchars=eol:$ sidescrolloff=0
1154 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001155endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001156
Bram Moolenaarbdd2c292020-06-22 21:34:30 +02001157" Test for commands that scroll the window horizontally. Test with folds.
1158" H, M, L, CTRL-E, CTRL-Y, CTRL-U, CTRL-D, PageUp, PageDown commands
1159func Test_vert_scroll_cmds()
Bram Moolenaar1671f442020-03-10 07:48:13 +01001160 15new
1161 call setline(1, range(1, 100))
1162 exe "normal! 30ggz\<CR>"
1163 set foldenable
1164 33,36fold
1165 40,43fold
1166 46,49fold
1167 let h = winheight(0)
Bram Moolenaarbdd2c292020-06-22 21:34:30 +02001168
1169 " Test for H, M and L commands
Bram Moolenaar1671f442020-03-10 07:48:13 +01001170 " Top of the screen = 30
1171 " Folded lines = 9
1172 " Bottom of the screen = 30 + h + 9 - 1
1173 normal! 4L
1174 call assert_equal(35 + h, line('.'))
1175 normal! 4H
1176 call assert_equal(33, line('.'))
Bram Moolenaarbdd2c292020-06-22 21:34:30 +02001177
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02001178 " Test for using a large count value
1179 %d
1180 call setline(1, range(1, 4))
1181 norm! 6H
1182 call assert_equal(4, line('.'))
1183
1184 " Test for 'M' with folded lines
1185 %d
1186 call setline(1, range(1, 20))
1187 1,5fold
1188 norm! LM
1189 call assert_equal(12, line('.'))
1190
Bram Moolenaarbdd2c292020-06-22 21:34:30 +02001191 " Test for the CTRL-E and CTRL-Y commands with folds
1192 %d
1193 call setline(1, range(1, 10))
1194 3,5fold
1195 exe "normal 6G3\<C-E>"
1196 call assert_equal(6, line('w0'))
1197 exe "normal 2\<C-Y>"
1198 call assert_equal(2, line('w0'))
1199
1200 " Test for CTRL-Y on a folded line
1201 %d
1202 call setline(1, range(1, 100))
1203 exe (h + 2) .. "," .. (h + 4) .. "fold"
1204 exe h + 5
1205 normal z-
1206 exe "normal \<C-Y>\<C-Y>"
1207 call assert_equal(h + 1, line('w$'))
1208
Bram Moolenaard1ad99b2020-10-04 16:16:54 +02001209 " Test for CTRL-Y from the first line and CTRL-E from the last line
1210 %d
1211 set scrolloff=2
1212 call setline(1, range(1, 4))
1213 exe "normal gg\<C-Y>"
1214 call assert_equal(1, line('w0'))
1215 call assert_equal(1, line('.'))
1216 exe "normal G4\<C-E>\<C-E>"
1217 call assert_equal(4, line('w$'))
1218 call assert_equal(4, line('.'))
1219 set scrolloff&
1220
Bram Moolenaarbdd2c292020-06-22 21:34:30 +02001221 " Using <PageUp> and <PageDown> in an empty buffer should beep
1222 %d
1223 call assert_beeps('exe "normal \<PageUp>"')
1224 call assert_beeps('exe "normal \<C-B>"')
1225 call assert_beeps('exe "normal \<PageDown>"')
1226 call assert_beeps('exe "normal \<C-F>"')
1227
1228 " Test for <C-U> and <C-D> with fold
1229 %d
1230 call setline(1, range(1, 100))
1231 10,35fold
1232 set scroll=10
1233 exe "normal \<C-D>"
1234 call assert_equal(36, line('.'))
1235 exe "normal \<C-D>"
1236 call assert_equal(46, line('.'))
1237 exe "normal \<C-U>"
1238 call assert_equal(36, line('.'))
1239 exe "normal \<C-U>"
1240 call assert_equal(10, line('.'))
1241 exe "normal \<C-U>"
1242 call assert_equal(1, line('.'))
1243 set scroll&
1244
1245 " Test for scrolling to the top of the file with <C-U> and a fold
1246 10
1247 normal ztL
1248 exe "normal \<C-U>\<C-U>"
1249 call assert_equal(1, line('w0'))
1250
1251 " Test for CTRL-D on a folded line
1252 %d
1253 call setline(1, range(1, 100))
1254 50,100fold
1255 75
1256 normal z-
1257 exe "normal \<C-D>"
1258 call assert_equal(50, line('.'))
1259 call assert_equal(100, line('w$'))
1260 normal z.
1261 let lnum = winline()
1262 exe "normal \<C-D>"
1263 call assert_equal(lnum, winline())
1264 call assert_equal(50, line('.'))
1265 normal zt
1266 exe "normal \<C-D>"
1267 call assert_equal(50, line('w0'))
1268
Bram Moolenaard1ad99b2020-10-04 16:16:54 +02001269 " Test for <S-CR>. Page down.
1270 %d
1271 call setline(1, range(1, 100))
1272 call feedkeys("\<S-CR>", 'xt')
1273 call assert_equal(14, line('w0'))
1274 call assert_equal(28, line('w$'))
1275
1276 " Test for <S-->. Page up.
1277 call feedkeys("\<S-->", 'xt')
1278 call assert_equal(1, line('w0'))
1279 call assert_equal(15, line('w$'))
1280
Bram Moolenaar1671f442020-03-10 07:48:13 +01001281 set foldenable&
1282 close!
1283endfunc
1284
Bram Moolenaar777e7c22021-10-25 17:07:04 +01001285func Test_scroll_in_ex_mode()
1286 " This was using invalid memory because w_botline was invalid.
1287 let lines =<< trim END
1288 diffsplit
1289 norm os00(
1290 call writefile(['done'], 'Xdone')
1291 qa!
1292 END
Bram Moolenaarb152b6a2022-09-29 21:37:33 +01001293 call writefile(lines, 'Xscript', 'D')
Bram Moolenaar777e7c22021-10-25 17:07:04 +01001294 call assert_equal(1, RunVim([], [], '--clean -X -Z -e -s -S Xscript'))
1295 call assert_equal(['done'], readfile('Xdone'))
1296
Bram Moolenaar777e7c22021-10-25 17:07:04 +01001297 call delete('Xdone')
1298endfunc
1299
Bram Moolenaarbdd2c292020-06-22 21:34:30 +02001300" Test for the 'sidescroll' option
1301func Test_sidescroll_opt()
1302 new
1303 20vnew
1304
1305 " scroll by 2 characters horizontally
1306 set sidescroll=2 nowrap
1307 call setline(1, repeat('a', 40))
1308 normal g$l
1309 call assert_equal(19, screenpos(0, 1, 21).col)
1310 normal l
1311 call assert_equal(20, screenpos(0, 1, 22).col)
1312 normal g0h
1313 call assert_equal(2, screenpos(0, 1, 2).col)
1314 call assert_equal(20, screenpos(0, 1, 20).col)
1315
1316 " when 'sidescroll' is 0, cursor positioned at the center
1317 set sidescroll=0
1318 normal g$l
1319 call assert_equal(11, screenpos(0, 1, 21).col)
1320 normal g0h
1321 call assert_equal(10, screenpos(0, 1, 10).col)
1322
1323 %bw!
1324 set wrap& sidescroll&
1325endfunc
1326
Bram Moolenaar004a6782020-04-11 17:09:31 +02001327" basic tests for foldopen/folddelete
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001328func Test_normal18_z_fold()
Bram Moolenaar004a6782020-04-11 17:09:31 +02001329 CheckFeature folding
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001330 call Setup_NewWindow()
1331 50
1332 setl foldenable fdm=marker foldlevel=5
1333
Bram Moolenaar1671f442020-03-10 07:48:13 +01001334 call assert_beeps('normal! zj')
1335 call assert_beeps('normal! zk')
1336
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001337 " Test for zF
1338 " First fold
1339 norm! 4zF
1340 " check that folds have been created
1341 call assert_equal(['50/*{{{*/', '51', '52', '53/*}}}*/'], getline(50,53))
1342
1343 " Test for zd
1344 51
1345 norm! 2zF
1346 call assert_equal(2, foldlevel('.'))
1347 norm! kzd
1348 call assert_equal(['50', '51/*{{{*/', '52/*}}}*/', '53'], getline(50,53))
1349 norm! j
1350 call assert_equal(1, foldlevel('.'))
1351
1352 " Test for zD
1353 " also deletes partially selected folds recursively
1354 51
1355 norm! zF
1356 call assert_equal(2, foldlevel('.'))
1357 norm! kV2jzD
1358 call assert_equal(['50', '51', '52', '53'], getline(50,53))
1359
1360 " Test for zE
1361 85
1362 norm! 4zF
1363 86
1364 norm! 2zF
1365 90
1366 norm! 4zF
1367 call assert_equal(['85/*{{{*/', '86/*{{{*/', '87/*}}}*/', '88/*}}}*/', '89', '90/*{{{*/', '91', '92', '93/*}}}*/'], getline(85,93))
1368 norm! zE
1369 call assert_equal(['85', '86', '87', '88', '89', '90', '91', '92', '93'], getline(85,93))
1370
1371 " Test for zn
1372 50
1373 set foldlevel=0
1374 norm! 2zF
1375 norm! zn
1376 norm! k
1377 call assert_equal('49', getline('.'))
1378 norm! j
1379 call assert_equal('50/*{{{*/', getline('.'))
1380 norm! j
1381 call assert_equal('51/*}}}*/', getline('.'))
1382 norm! j
1383 call assert_equal('52', getline('.'))
1384 call assert_equal(0, &foldenable)
1385
1386 " Test for zN
1387 49
1388 norm! zN
1389 call assert_equal('49', getline('.'))
1390 norm! j
1391 call assert_equal('50/*{{{*/', getline('.'))
1392 norm! j
1393 call assert_equal('52', getline('.'))
1394 call assert_equal(1, &foldenable)
1395
1396 " Test for zi
1397 norm! zi
1398 call assert_equal(0, &foldenable)
1399 norm! zi
1400 call assert_equal(1, &foldenable)
1401 norm! zi
1402 call assert_equal(0, &foldenable)
1403 norm! zi
1404 call assert_equal(1, &foldenable)
1405
1406 " Test for za
1407 50
1408 norm! za
1409 norm! k
1410 call assert_equal('49', getline('.'))
1411 norm! j
1412 call assert_equal('50/*{{{*/', getline('.'))
1413 norm! j
1414 call assert_equal('51/*}}}*/', getline('.'))
1415 norm! j
1416 call assert_equal('52', getline('.'))
1417 50
1418 norm! za
1419 norm! k
1420 call assert_equal('49', getline('.'))
1421 norm! j
1422 call assert_equal('50/*{{{*/', getline('.'))
1423 norm! j
1424 call assert_equal('52', getline('.'))
1425
1426 49
1427 norm! 5zF
1428 norm! k
1429 call assert_equal('48', getline('.'))
1430 norm! j
1431 call assert_equal('49/*{{{*/', getline('.'))
1432 norm! j
1433 call assert_equal('55', getline('.'))
1434 49
1435 norm! za
1436 call assert_equal('49/*{{{*/', getline('.'))
1437 norm! j
1438 call assert_equal('50/*{{{*/', getline('.'))
1439 norm! j
1440 call assert_equal('52', getline('.'))
1441 set nofoldenable
1442 " close fold and set foldenable
1443 norm! za
1444 call assert_equal(1, &foldenable)
1445
1446 50
1447 " have to use {count}za to open all folds and make the cursor visible
1448 norm! 2za
1449 norm! 2k
1450 call assert_equal('48', getline('.'))
1451 norm! j
1452 call assert_equal('49/*{{{*/', getline('.'))
1453 norm! j
1454 call assert_equal('50/*{{{*/', getline('.'))
1455 norm! j
1456 call assert_equal('51/*}}}*/', getline('.'))
1457 norm! j
1458 call assert_equal('52', getline('.'))
1459
1460 " Test for zA
1461 49
1462 set foldlevel=0
1463 50
1464 norm! zA
1465 norm! 2k
1466 call assert_equal('48', getline('.'))
1467 norm! j
1468 call assert_equal('49/*{{{*/', getline('.'))
1469 norm! j
1470 call assert_equal('50/*{{{*/', getline('.'))
1471 norm! j
1472 call assert_equal('51/*}}}*/', getline('.'))
1473 norm! j
1474 call assert_equal('52', getline('.'))
1475
Dominique Pelle923dce22021-11-21 11:36:04 +00001476 " zA on an opened fold when foldenable is not set
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001477 50
1478 set nofoldenable
1479 norm! zA
1480 call assert_equal(1, &foldenable)
1481 norm! k
1482 call assert_equal('48', getline('.'))
1483 norm! j
1484 call assert_equal('49/*{{{*/', getline('.'))
1485 norm! j
1486 call assert_equal('55', getline('.'))
1487
1488 " Test for zc
1489 norm! zE
1490 50
1491 norm! 2zF
1492 49
1493 norm! 5zF
1494 set nofoldenable
1495 50
1496 " There most likely is a bug somewhere:
1497 " https://groups.google.com/d/msg/vim_dev/v2EkfJ_KQjI/u-Cvv94uCAAJ
1498 " TODO: Should this only close the inner most fold or both folds?
1499 norm! zc
1500 call assert_equal(1, &foldenable)
1501 norm! k
1502 call assert_equal('48', getline('.'))
1503 norm! j
1504 call assert_equal('49/*{{{*/', getline('.'))
1505 norm! j
1506 call assert_equal('55', getline('.'))
1507 set nofoldenable
1508 50
1509 norm! Vjzc
1510 norm! k
1511 call assert_equal('48', getline('.'))
1512 norm! j
1513 call assert_equal('49/*{{{*/', getline('.'))
1514 norm! j
1515 call assert_equal('55', getline('.'))
1516
1517 " Test for zC
1518 set nofoldenable
1519 50
1520 norm! zCk
1521 call assert_equal('48', getline('.'))
1522 norm! j
1523 call assert_equal('49/*{{{*/', getline('.'))
1524 norm! j
1525 call assert_equal('55', getline('.'))
1526
1527 " Test for zx
1528 " 1) close folds at line 49-54
1529 set nofoldenable
1530 48
1531 norm! zx
1532 call assert_equal(1, &foldenable)
1533 norm! j
1534 call assert_equal('49/*{{{*/', getline('.'))
1535 norm! j
1536 call assert_equal('55', getline('.'))
1537
Bram Moolenaar395b6ba2017-04-07 20:09:51 +02001538 " 2) do not close fold under cursor
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001539 51
1540 set nofoldenable
1541 norm! zx
1542 call assert_equal(1, &foldenable)
1543 norm! 3k
1544 call assert_equal('48', getline('.'))
1545 norm! j
1546 call assert_equal('49/*{{{*/', getline('.'))
1547 norm! j
1548 call assert_equal('50/*{{{*/', getline('.'))
1549 norm! j
1550 call assert_equal('51/*}}}*/', getline('.'))
1551 norm! j
1552 call assert_equal('52', getline('.'))
1553 norm! j
1554 call assert_equal('53', getline('.'))
1555 norm! j
1556 call assert_equal('54/*}}}*/', getline('.'))
1557 norm! j
1558 call assert_equal('55', getline('.'))
1559
1560 " 3) close one level of folds
1561 48
1562 set nofoldenable
1563 set foldlevel=1
1564 norm! zx
1565 call assert_equal(1, &foldenable)
1566 call assert_equal('48', getline('.'))
1567 norm! j
1568 call assert_equal('49/*{{{*/', getline('.'))
1569 norm! j
1570 call assert_equal('50/*{{{*/', getline('.'))
1571 norm! j
1572 call assert_equal('52', getline('.'))
1573 norm! j
1574 call assert_equal('53', getline('.'))
1575 norm! j
1576 call assert_equal('54/*}}}*/', getline('.'))
1577 norm! j
1578 call assert_equal('55', getline('.'))
1579
1580 " Test for zX
1581 " Close all folds
1582 set foldlevel=0 nofoldenable
1583 50
1584 norm! zX
1585 call assert_equal(1, &foldenable)
1586 norm! k
1587 call assert_equal('48', getline('.'))
1588 norm! j
1589 call assert_equal('49/*{{{*/', getline('.'))
1590 norm! j
1591 call assert_equal('55', getline('.'))
1592
1593 " Test for zm
1594 50
1595 set nofoldenable foldlevel=2
1596 norm! zm
1597 call assert_equal(1, &foldenable)
1598 call assert_equal(1, &foldlevel)
1599 norm! zm
1600 call assert_equal(0, &foldlevel)
1601 norm! zm
1602 call assert_equal(0, &foldlevel)
1603 norm! k
1604 call assert_equal('48', getline('.'))
1605 norm! j
1606 call assert_equal('49/*{{{*/', getline('.'))
1607 norm! j
1608 call assert_equal('55', getline('.'))
1609
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02001610 " Test for zm with a count
1611 50
1612 set foldlevel=2
1613 norm! 3zm
1614 call assert_equal(0, &foldlevel)
1615 call assert_equal(49, foldclosed(line('.')))
1616
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001617 " Test for zM
1618 48
1619 set nofoldenable foldlevel=99
1620 norm! zM
1621 call assert_equal(1, &foldenable)
1622 call assert_equal(0, &foldlevel)
1623 call assert_equal('48', getline('.'))
1624 norm! j
1625 call assert_equal('49/*{{{*/', getline('.'))
1626 norm! j
1627 call assert_equal('55', getline('.'))
1628
1629 " Test for zr
1630 48
1631 set nofoldenable foldlevel=0
1632 norm! zr
1633 call assert_equal(0, &foldenable)
1634 call assert_equal(1, &foldlevel)
1635 set foldlevel=0 foldenable
1636 norm! zr
1637 call assert_equal(1, &foldenable)
1638 call assert_equal(1, &foldlevel)
1639 norm! zr
1640 call assert_equal(2, &foldlevel)
1641 call assert_equal('48', getline('.'))
1642 norm! j
1643 call assert_equal('49/*{{{*/', getline('.'))
1644 norm! j
1645 call assert_equal('50/*{{{*/', getline('.'))
1646 norm! j
1647 call assert_equal('51/*}}}*/', getline('.'))
1648 norm! j
1649 call assert_equal('52', getline('.'))
1650
1651 " Test for zR
1652 48
1653 set nofoldenable foldlevel=0
1654 norm! zR
1655 call assert_equal(0, &foldenable)
1656 call assert_equal(2, &foldlevel)
1657 set foldenable foldlevel=0
1658 norm! zR
1659 call assert_equal(1, &foldenable)
1660 call assert_equal(2, &foldlevel)
1661 call assert_equal('48', getline('.'))
1662 norm! j
1663 call assert_equal('49/*{{{*/', getline('.'))
1664 norm! j
1665 call assert_equal('50/*{{{*/', getline('.'))
1666 norm! j
1667 call assert_equal('51/*}}}*/', getline('.'))
1668 norm! j
1669 call assert_equal('52', getline('.'))
1670 call append(50, ['a /*{{{*/', 'b /*}}}*/'])
1671 48
1672 call assert_equal('48', getline('.'))
1673 norm! j
1674 call assert_equal('49/*{{{*/', getline('.'))
1675 norm! j
1676 call assert_equal('50/*{{{*/', getline('.'))
1677 norm! j
1678 call assert_equal('a /*{{{*/', getline('.'))
1679 norm! j
1680 call assert_equal('51/*}}}*/', getline('.'))
1681 norm! j
1682 call assert_equal('52', getline('.'))
1683 48
1684 norm! zR
1685 call assert_equal(1, &foldenable)
1686 call assert_equal(3, &foldlevel)
1687 call assert_equal('48', getline('.'))
1688 norm! j
1689 call assert_equal('49/*{{{*/', getline('.'))
1690 norm! j
1691 call assert_equal('50/*{{{*/', getline('.'))
1692 norm! j
1693 call assert_equal('a /*{{{*/', getline('.'))
1694 norm! j
1695 call assert_equal('b /*}}}*/', getline('.'))
1696 norm! j
1697 call assert_equal('51/*}}}*/', getline('.'))
1698 norm! j
1699 call assert_equal('52', getline('.'))
1700
1701 " clean up
1702 setl nofoldenable fdm=marker foldlevel=0
1703 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001704endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001705
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001706func Test_normal20_exmode()
Bram Moolenaar004a6782020-04-11 17:09:31 +02001707 " Reading from redirected file doesn't work on MS-Windows
1708 CheckNotMSWindows
Bram Moolenaarb152b6a2022-09-29 21:37:33 +01001709 call writefile(['1a', 'foo', 'bar', '.', 'w! Xn20file2', 'q!'], 'Xn20script', 'D')
1710 call writefile(['1', '2'], 'Xn20file', 'D')
Bram Moolenaarb18b4962022-09-02 21:55:50 +01001711 call system(GetVimCommand() .. ' -e -s < Xn20script Xn20file')
Bram Moolenaarb152b6a2022-09-29 21:37:33 +01001712 let a = readfile('Xn20file2')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001713 call assert_equal(['1', 'foo', 'bar', '2'], a)
1714
1715 " clean up
Bram Moolenaarb152b6a2022-09-29 21:37:33 +01001716 call delete('Xn20file2')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001717 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001718endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001719
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001720func Test_normal21_nv_hat()
1721
1722 " Edit a fresh file and wipe the buffer list so that there is no alternate
1723 " file present. Next, check for the expected command failures.
1724 edit Xfoo | %bw
Bram Moolenaare2e40752020-09-04 21:18:46 +02001725 call assert_fails(':buffer #', 'E86:')
1726 call assert_fails(':execute "normal! \<C-^>"', 'E23:')
Bram Moolenaarb7e24832020-06-24 13:37:35 +02001727 call assert_fails("normal i\<C-R>#", 'E23:')
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001728
1729 " Test for the expected behavior when switching between two named buffers.
1730 edit Xfoo | edit Xbar
1731 call feedkeys("\<C-^>", 'tx')
1732 call assert_equal('Xfoo', fnamemodify(bufname('%'), ':t'))
1733 call feedkeys("\<C-^>", 'tx')
1734 call assert_equal('Xbar', fnamemodify(bufname('%'), ':t'))
1735
1736 " Test for the expected behavior when only one buffer is named.
1737 enew | let l:nr = bufnr('%')
1738 call feedkeys("\<C-^>", 'tx')
1739 call assert_equal('Xbar', fnamemodify(bufname('%'), ':t'))
1740 call feedkeys("\<C-^>", 'tx')
1741 call assert_equal('', bufname('%'))
1742 call assert_equal(l:nr, bufnr('%'))
1743
1744 " Test that no action is taken by "<C-^>" when an operator is pending.
1745 edit Xfoo
1746 call feedkeys("ci\<C-^>", 'tx')
1747 call assert_equal('Xfoo', fnamemodify(bufname('%'), ':t'))
1748
1749 %bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001750endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001751
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001752func Test_normal22_zet()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001753 " Test for ZZ
Bram Moolenaar0913a102016-09-03 19:11:59 +02001754 " let shell = &shell
1755 " let &shell = 'sh'
Bram Moolenaarb152b6a2022-09-29 21:37:33 +01001756 call writefile(['1', '2'], 'Xn22file', 'D')
Bram Moolenaar93344c22019-08-14 21:12:05 +02001757 let args = ' -N -i NONE --noplugins -X --not-a-term'
Bram Moolenaarb18b4962022-09-02 21:55:50 +01001758 call system(GetVimCommand() .. args .. ' -c "%d" -c ":norm! ZZ" Xn22file')
1759 let a = readfile('Xn22file')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001760 call assert_equal([], a)
1761 " Test for ZQ
Bram Moolenaarb18b4962022-09-02 21:55:50 +01001762 call writefile(['1', '2'], 'Xn22file')
1763 call system(GetVimCommand() . args . ' -c "%d" -c ":norm! ZQ" Xn22file')
1764 let a = readfile('Xn22file')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001765 call assert_equal(['1', '2'], a)
1766
Bram Moolenaar1671f442020-03-10 07:48:13 +01001767 " Unsupported Z command
1768 call assert_beeps('normal! ZW')
1769
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001770 " clean up
Bram Moolenaar0913a102016-09-03 19:11:59 +02001771 " let &shell = shell
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001772endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001773
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001774func Test_normal23_K()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001775 " Test for K command
1776 new
Bram Moolenaar426f3752016-11-04 21:22:37 +01001777 call append(0, ['version8.txt', 'man', 'aa%bb', 'cc|dd'])
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001778 let k = &keywordprg
1779 set keywordprg=:help
1780 1
1781 norm! VK
1782 call assert_equal('version8.txt', fnamemodify(bufname('%'), ':t'))
1783 call assert_equal('help', &ft)
1784 call assert_match('\*version8.txt\*', getline('.'))
1785 helpclose
1786 norm! 0K
1787 call assert_equal('version8.txt', fnamemodify(bufname('%'), ':t'))
1788 call assert_equal('help', &ft)
Bram Moolenaarb1c91982018-05-17 17:04:55 +02001789 call assert_match('\*version8\.\d\*', getline('.'))
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001790 helpclose
1791
Bram Moolenaar426f3752016-11-04 21:22:37 +01001792 set keywordprg=:new
1793 set iskeyword+=%
1794 set iskeyword+=\|
1795 2
1796 norm! K
1797 call assert_equal('man', fnamemodify(bufname('%'), ':t'))
1798 bwipe!
1799 3
1800 norm! K
1801 call assert_equal('aa%bb', fnamemodify(bufname('%'), ':t'))
1802 bwipe!
Bram Moolenaareb828d02016-11-05 19:54:01 +01001803 if !has('win32')
1804 4
1805 norm! K
1806 call assert_equal('cc|dd', fnamemodify(bufname('%'), ':t'))
1807 bwipe!
1808 endif
Bram Moolenaar426f3752016-11-04 21:22:37 +01001809 set iskeyword-=%
1810 set iskeyword-=\|
1811
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02001812 " Test for specifying a count to K
1813 1
1814 com! -nargs=* Kprog let g:Kprog_Args = <q-args>
1815 set keywordprg=:Kprog
1816 norm! 3K
1817 call assert_equal('3 version8', g:Kprog_Args)
1818 delcom Kprog
1819
Bram Moolenaar0913a102016-09-03 19:11:59 +02001820 " Only expect "man" to work on Unix
1821 if !has("unix")
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001822 let &keywordprg = k
1823 bw!
1824 return
1825 endif
Bram Moolenaarc6b37db2019-04-27 18:00:34 +02001826
Bram Moolenaar9134f1e2019-11-29 20:26:13 +01001827 let not_gnu_man = has('mac') || has('bsd')
1828 if not_gnu_man
Dominique Pelle923dce22021-11-21 11:36:04 +00001829 " In macOS and BSD, the option for specifying a pager is different
Bram Moolenaarc6b37db2019-04-27 18:00:34 +02001830 set keywordprg=man\ -P\ cat
1831 else
1832 set keywordprg=man\ --pager=cat
1833 endif
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001834 " Test for using man
1835 2
1836 let a = execute('unsilent norm! K')
Bram Moolenaar9134f1e2019-11-29 20:26:13 +01001837 if not_gnu_man
Bram Moolenaarc6b37db2019-04-27 18:00:34 +02001838 call assert_match("man -P cat 'man'", a)
1839 else
1840 call assert_match("man --pager=cat 'man'", a)
1841 endif
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001842
Bram Moolenaar1671f442020-03-10 07:48:13 +01001843 " Error cases
1844 call setline(1, '#$#')
1845 call assert_fails('normal! ggK', 'E349:')
1846 call setline(1, '---')
1847 call assert_fails('normal! ggv2lK', 'E349:')
1848 call setline(1, ['abc', 'xyz'])
Bram Moolenaar9b7bf9e2020-07-11 22:14:59 +02001849 call assert_fails("normal! gg2lv2h\<C-]>", 'E433:')
Bram Moolenaar1671f442020-03-10 07:48:13 +01001850 call assert_beeps("normal! ggVjK")
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02001851 norm! V
1852 call assert_beeps("norm! cK")
Bram Moolenaar1671f442020-03-10 07:48:13 +01001853
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001854 " clean up
1855 let &keywordprg = k
1856 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001857endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001858
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001859func Test_normal24_rot13()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001860 " Testing for g?? g?g?
1861 new
1862 call append(0, 'abcdefghijklmnopqrstuvwxyzäüö')
1863 1
1864 norm! g??
1865 call assert_equal('nopqrstuvwxyzabcdefghijklmäüö', getline('.'))
1866 norm! g?g?
1867 call assert_equal('abcdefghijklmnopqrstuvwxyzäüö', getline('.'))
1868
1869 " clean up
1870 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001871endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001872
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001873func Test_normal25_tag()
Bram Moolenaar5a4c3082019-12-01 15:23:11 +01001874 CheckFeature quickfix
1875
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001876 " Testing for CTRL-] g CTRL-] g]
1877 " CTRL-W g] CTRL-W CTRL-] CTRL-W g CTRL-]
1878 h
1879 " Test for CTRL-]
1880 call search('\<x\>$')
1881 exe "norm! \<c-]>"
1882 call assert_equal("change.txt", fnamemodify(bufname('%'), ':t'))
1883 norm! yiW
1884 call assert_equal("*x*", @0)
1885 exe ":norm \<c-o>"
1886
1887 " Test for g_CTRL-]
1888 call search('\<v_u\>$')
1889 exe "norm! g\<c-]>"
1890 call assert_equal("change.txt", fnamemodify(bufname('%'), ':t'))
1891 norm! yiW
1892 call assert_equal("*v_u*", @0)
1893 exe ":norm \<c-o>"
1894
1895 " Test for g]
1896 call search('\<i_<Esc>$')
1897 let a = execute(":norm! g]")
1898 call assert_match('i_<Esc>.*insert.txt', a)
1899
1900 if !empty(exepath('cscope')) && has('cscope')
1901 " setting cscopetag changes how g] works
1902 set cst
1903 exe "norm! g]"
1904 call assert_equal("insert.txt", fnamemodify(bufname('%'), ':t'))
1905 norm! yiW
1906 call assert_equal("*i_<Esc>*", @0)
1907 exe ":norm \<c-o>"
1908 " Test for CTRL-W g]
1909 exe "norm! \<C-W>g]"
1910 call assert_equal("insert.txt", fnamemodify(bufname('%'), ':t'))
1911 norm! yiW
1912 call assert_equal("*i_<Esc>*", @0)
1913 call assert_equal(3, winnr('$'))
1914 helpclose
1915 set nocst
1916 endif
1917
1918 " Test for CTRL-W g]
1919 let a = execute("norm! \<C-W>g]")
1920 call assert_match('i_<Esc>.*insert.txt', a)
1921
1922 " Test for CTRL-W CTRL-]
1923 exe "norm! \<C-W>\<C-]>"
1924 call assert_equal("insert.txt", fnamemodify(bufname('%'), ':t'))
1925 norm! yiW
1926 call assert_equal("*i_<Esc>*", @0)
1927 call assert_equal(3, winnr('$'))
1928 helpclose
1929
1930 " Test for CTRL-W g CTRL-]
1931 exe "norm! \<C-W>g\<C-]>"
1932 call assert_equal("insert.txt", fnamemodify(bufname('%'), ':t'))
1933 norm! yiW
1934 call assert_equal("*i_<Esc>*", @0)
1935 call assert_equal(3, winnr('$'))
1936 helpclose
1937
1938 " clean up
1939 helpclose
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001940endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001941
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001942func Test_normal26_put()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001943 " Test for ]p ]P [p and [P
1944 new
1945 call append(0, ['while read LINE', 'do', ' ((count++))', ' if [ $? -ne 0 ]; then', " echo 'Error writing file'", ' fi', 'done'])
1946 1
1947 /Error/y a
1948 2
1949 norm! "a]pj"a[p
1950 call assert_equal(['do', "echo 'Error writing file'", " echo 'Error writing file'", ' ((count++))'], getline(2,5))
1951 1
1952 /^\s\{4}/
1953 exe "norm! \"a]P3Eldt'"
1954 exe "norm! j\"a[P2Eldt'"
1955 call assert_equal([' if [ $? -ne 0 ]; then', " echo 'Error writing'", " echo 'Error'", " echo 'Error writing file'", ' fi'], getline(6,10))
1956
1957 " clean up
1958 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02001959endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001960
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01001961func Test_normal27_bracket()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001962 " Test for [' [` ]' ]`
1963 call Setup_NewWindow()
1964 1,21s/.\+/ & b/
1965 1
1966 norm! $ma
1967 5
1968 norm! $mb
1969 10
1970 norm! $mc
1971 15
1972 norm! $md
1973 20
1974 norm! $me
1975
1976 " Test for ['
1977 9
1978 norm! 2['
1979 call assert_equal(' 1 b', getline('.'))
1980 call assert_equal(1, line('.'))
1981 call assert_equal(3, col('.'))
1982
1983 " Test for ]'
1984 norm! ]'
1985 call assert_equal(' 5 b', getline('.'))
1986 call assert_equal(5, line('.'))
1987 call assert_equal(3, col('.'))
1988
zeertzjqcf344342022-07-06 12:57:31 +01001989 " No mark before line 1, cursor moves to first non-blank on current line
1990 1
1991 norm! 5|['
1992 call assert_equal(' 1 b', getline('.'))
1993 call assert_equal(1, line('.'))
1994 call assert_equal(3, col('.'))
1995
1996 " No mark after line 21, cursor moves to first non-blank on current line
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001997 21
zeertzjqcf344342022-07-06 12:57:31 +01001998 norm! 5|]'
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02001999 call assert_equal(' 21 b', getline('.'))
2000 call assert_equal(21, line('.'))
2001 call assert_equal(3, col('.'))
2002
2003 " Test for [`
2004 norm! 2[`
2005 call assert_equal(' 15 b', getline('.'))
2006 call assert_equal(15, line('.'))
2007 call assert_equal(8, col('.'))
2008
2009 " Test for ]`
2010 norm! ]`
2011 call assert_equal(' 20 b', getline('.'))
2012 call assert_equal(20, line('.'))
2013 call assert_equal(8, col('.'))
2014
zeertzjqcf344342022-07-06 12:57:31 +01002015 " No mark before line 1, cursor does not move
2016 1
2017 norm! 5|[`
2018 call assert_equal(' 1 b', getline('.'))
2019 call assert_equal(1, line('.'))
2020 call assert_equal(5, col('.'))
2021
2022 " No mark after line 21, cursor does not move
2023 21
2024 norm! 5|]`
2025 call assert_equal(' 21 b', getline('.'))
2026 call assert_equal(21, line('.'))
2027 call assert_equal(5, col('.'))
2028
2029 " Count too large for [`
2030 " cursor moves to first lowercase mark
2031 norm! 99[`
2032 call assert_equal(' 1 b', getline('.'))
2033 call assert_equal(1, line('.'))
2034 call assert_equal(7, col('.'))
2035
2036 " Count too large for ]`
2037 " cursor moves to last lowercase mark
2038 norm! 99]`
2039 call assert_equal(' 20 b', getline('.'))
2040 call assert_equal(20, line('.'))
2041 call assert_equal(8, col('.'))
2042
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002043 " clean up
2044 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002045endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002046
Bram Moolenaar1671f442020-03-10 07:48:13 +01002047" Test for ( and ) sentence movements
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01002048func Test_normal28_parenthesis()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002049 new
2050 call append(0, ['This is a test. With some sentences!', '', 'Even with a question? And one more. And no sentence here'])
2051
2052 $
2053 norm! d(
2054 call assert_equal(['This is a test. With some sentences!', '', 'Even with a question? And one more. ', ''], getline(1, '$'))
2055 norm! 2d(
2056 call assert_equal(['This is a test. With some sentences!', '', ' ', ''], getline(1, '$'))
2057 1
2058 norm! 0d)
2059 call assert_equal(['With some sentences!', '', ' ', ''], getline(1, '$'))
2060
2061 call append('$', ['This is a long sentence', '', 'spanning', 'over several lines. '])
2062 $
2063 norm! $d(
2064 call assert_equal(['With some sentences!', '', ' ', '', 'This is a long sentence', ''], getline(1, '$'))
2065
Bram Moolenaar224a5f12020-04-28 20:29:07 +02002066 " Move to the next sentence from a paragraph macro
2067 %d
2068 call setline(1, ['.LP', 'blue sky!. blue sky.', 'blue sky. blue sky.'])
2069 call cursor(1, 1)
2070 normal )
2071 call assert_equal([2, 1], [line('.'), col('.')])
2072 normal )
2073 call assert_equal([2, 12], [line('.'), col('.')])
2074 normal ((
2075 call assert_equal([1, 1], [line('.'), col('.')])
2076
Bram Moolenaar1671f442020-03-10 07:48:13 +01002077 " It is an error if a next sentence is not found
2078 %d
2079 call setline(1, '.SH')
2080 call assert_beeps('normal )')
2081
Bram Moolenaar224a5f12020-04-28 20:29:07 +02002082 " If only dot is present, don't treat that as a sentence
2083 call setline(1, '. This is a sentence.')
2084 normal $((
2085 call assert_equal(3, col('.'))
2086
Bram Moolenaar1671f442020-03-10 07:48:13 +01002087 " Jumping to a fold should open the fold
2088 call setline(1, ['', '', 'one', 'two', 'three'])
2089 set foldenable
2090 2,$fold
2091 call feedkeys(')', 'xt')
2092 call assert_equal(3, line('.'))
2093 call assert_equal(1, foldlevel('.'))
2094 call assert_equal(-1, foldclosed('.'))
2095 set foldenable&
2096
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002097 " clean up
2098 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002099endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002100
Bram Moolenaar1671f442020-03-10 07:48:13 +01002101" Test for { and } paragraph movements
2102func Test_normal29_brace()
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002103 let text =<< trim [DATA]
Bram Moolenaare7eb9272019-06-24 00:58:07 +02002104 A paragraph begins after each empty line, and also at each of a set of
2105 paragraph macros, specified by the pairs of characters in the 'paragraphs'
2106 option. The default is "IPLPPPQPP TPHPLIPpLpItpplpipbp", which corresponds to
2107 the macros ".IP", ".LP", etc. (These are nroff macros, so the dot must be in
2108 the first column). A section boundary is also a paragraph boundary.
2109 Note that a blank line (only containing white space) is NOT a paragraph
2110 boundary.
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002111
2112
Bram Moolenaare7eb9272019-06-24 00:58:07 +02002113 Also note that this does not include a '{' or '}' in the first column. When
2114 the '{' flag is in 'cpoptions' then '{' in the first column is used as a
2115 paragraph boundary |posix|.
2116 {
2117 This is no paragraph
2118 unless the '{' is set
2119 in 'cpoptions'
2120 }
2121 .IP
2122 The nroff macros IP separates a paragraph
2123 That means, it must be a '.'
2124 followed by IP
2125 .LPIt does not matter, if afterwards some
2126 more characters follow.
2127 .SHAlso section boundaries from the nroff
2128 macros terminate a paragraph. That means
2129 a character like this:
2130 .NH
2131 End of text here
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002132 [DATA]
2133
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002134 new
2135 call append(0, text)
2136 1
2137 norm! 0d2}
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002138
2139 let expected =<< trim [DATA]
Bram Moolenaare7eb9272019-06-24 00:58:07 +02002140 .IP
2141 The nroff macros IP separates a paragraph
2142 That means, it must be a '.'
2143 followed by IP
2144 .LPIt does not matter, if afterwards some
2145 more characters follow.
2146 .SHAlso section boundaries from the nroff
2147 macros terminate a paragraph. That means
2148 a character like this:
2149 .NH
2150 End of text here
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002151
2152 [DATA]
2153 call assert_equal(expected, getline(1, '$'))
2154
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002155 norm! 0d}
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002156
2157 let expected =<< trim [DATA]
Bram Moolenaare7eb9272019-06-24 00:58:07 +02002158 .LPIt does not matter, if afterwards some
2159 more characters follow.
2160 .SHAlso section boundaries from the nroff
2161 macros terminate a paragraph. That means
2162 a character like this:
2163 .NH
2164 End of text here
2165
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002166 [DATA]
2167 call assert_equal(expected, getline(1, '$'))
2168
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002169 $
2170 norm! d{
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002171
2172 let expected =<< trim [DATA]
Bram Moolenaare7eb9272019-06-24 00:58:07 +02002173 .LPIt does not matter, if afterwards some
2174 more characters follow.
2175 .SHAlso section boundaries from the nroff
2176 macros terminate a paragraph. That means
2177 a character like this:
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002178
2179 [DATA]
2180 call assert_equal(expected, getline(1, '$'))
2181
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002182 norm! d{
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002183
2184 let expected =<< trim [DATA]
Bram Moolenaare7eb9272019-06-24 00:58:07 +02002185 .LPIt does not matter, if afterwards some
2186 more characters follow.
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002187
2188 [DATA]
2189 call assert_equal(expected, getline(1, '$'))
2190
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002191 " Test with { in cpooptions
2192 %d
2193 call append(0, text)
2194 set cpo+={
2195 1
2196 norm! 0d2}
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002197
2198 let expected =<< trim [DATA]
Bram Moolenaare7eb9272019-06-24 00:58:07 +02002199 {
2200 This is no paragraph
2201 unless the '{' is set
2202 in 'cpoptions'
2203 }
2204 .IP
2205 The nroff macros IP separates a paragraph
2206 That means, it must be a '.'
2207 followed by IP
2208 .LPIt does not matter, if afterwards some
2209 more characters follow.
2210 .SHAlso section boundaries from the nroff
2211 macros terminate a paragraph. That means
2212 a character like this:
2213 .NH
2214 End of text here
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002215
2216 [DATA]
2217 call assert_equal(expected, getline(1, '$'))
2218
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002219 $
2220 norm! d}
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002221
2222 let expected =<< trim [DATA]
Bram Moolenaare7eb9272019-06-24 00:58:07 +02002223 {
2224 This is no paragraph
2225 unless the '{' is set
2226 in 'cpoptions'
2227 }
2228 .IP
2229 The nroff macros IP separates a paragraph
2230 That means, it must be a '.'
2231 followed by IP
2232 .LPIt does not matter, if afterwards some
2233 more characters follow.
2234 .SHAlso section boundaries from the nroff
2235 macros terminate a paragraph. That means
2236 a character like this:
2237 .NH
2238 End of text here
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002239
2240 [DATA]
2241 call assert_equal(expected, getline(1, '$'))
2242
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002243 norm! gg}
2244 norm! d5}
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002245
2246 let expected =<< trim [DATA]
Bram Moolenaare7eb9272019-06-24 00:58:07 +02002247 {
2248 This is no paragraph
2249 unless the '{' is set
2250 in 'cpoptions'
2251 }
Bram Moolenaarc79745a2019-05-20 22:12:34 +02002252
2253 [DATA]
2254 call assert_equal(expected, getline(1, '$'))
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002255
Bram Moolenaar1671f442020-03-10 07:48:13 +01002256 " Jumping to a fold should open the fold
2257 %d
2258 call setline(1, ['', 'one', 'two', ''])
2259 set foldenable
2260 2,$fold
2261 call feedkeys('}', 'xt')
2262 call assert_equal(4, line('.'))
2263 call assert_equal(1, foldlevel('.'))
2264 call assert_equal(-1, foldclosed('.'))
2265 set foldenable&
2266
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002267 " clean up
2268 set cpo-={
2269 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002270endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002271
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02002272" Test for section movements
2273func Test_normal_section()
2274 new
2275 let lines =<< trim [END]
2276 int foo()
2277 {
2278 if (1)
2279 {
2280 a = 1;
2281 }
2282 }
2283 [END]
2284 call setline(1, lines)
2285
2286 " jumping to a folded line using [[ should open the fold
2287 2,3fold
2288 call cursor(5, 1)
2289 call feedkeys("[[", 'xt')
2290 call assert_equal(2, line('.'))
2291 call assert_equal(-1, foldclosedend(line('.')))
2292
2293 close!
2294endfunc
2295
Bram Moolenaard1ad99b2020-10-04 16:16:54 +02002296" Test for changing case using u, U, gu, gU and ~ (tilde) commands
Bram Moolenaar1671f442020-03-10 07:48:13 +01002297func Test_normal30_changecase()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002298 new
2299 call append(0, 'This is a simple test: äüöß')
2300 norm! 1ggVu
2301 call assert_equal('this is a simple test: äüöß', getline('.'))
2302 norm! VU
2303 call assert_equal('THIS IS A SIMPLE TEST: ÄÜÖSS', getline('.'))
2304 norm! guu
2305 call assert_equal('this is a simple test: äüöss', getline('.'))
2306 norm! gUgU
2307 call assert_equal('THIS IS A SIMPLE TEST: ÄÜÖSS', getline('.'))
2308 norm! gugu
2309 call assert_equal('this is a simple test: äüöss', getline('.'))
2310 norm! gUU
2311 call assert_equal('THIS IS A SIMPLE TEST: ÄÜÖSS', getline('.'))
2312 norm! 010~
2313 call assert_equal('this is a SIMPLE TEST: ÄÜÖSS', getline('.'))
2314 norm! V~
2315 call assert_equal('THIS IS A simple test: äüöss', getline('.'))
Bram Moolenaard1ad99b2020-10-04 16:16:54 +02002316 call assert_beeps('norm! c~')
2317 %d
2318 call assert_beeps('norm! ~')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002319
Bram Moolenaar1671f442020-03-10 07:48:13 +01002320 " Test for changing case across lines using 'whichwrap'
2321 call setline(1, ['aaaaaa', 'aaaaaa'])
2322 normal! gg10~
2323 call assert_equal(['AAAAAA', 'aaaaaa'], getline(1, 2))
2324 set whichwrap+=~
2325 normal! gg10~
2326 call assert_equal(['aaaaaa', 'AAAAaa'], getline(1, 2))
2327 set whichwrap&
2328
Bram Moolenaar3e72dca2021-05-29 16:30:12 +02002329 " try changing the case with a double byte encoding (DBCS)
2330 %bw!
2331 let enc = &enc
2332 set encoding=cp932
2333 call setline(1, "\u8470")
2334 normal ~
2335 normal gU$gu$gUgUg~g~gugu
2336 call assert_equal("\u8470", getline(1))
2337 let &encoding = enc
2338
Bram Moolenaar1671f442020-03-10 07:48:13 +01002339 " clean up
2340 bw!
2341endfunc
2342
2343" Turkish ASCII turns to multi-byte. On some systems Turkish locale
2344" is available but toupper()/tolower() don't do the right thing.
2345func Test_normal_changecase_turkish()
2346 new
Bram Moolenaarf1c118b2018-09-03 22:08:10 +02002347 try
2348 lang tr_TR.UTF-8
2349 set casemap=
2350 let iupper = toupper('i')
2351 if iupper == "\u0130"
Bram Moolenaar9f4de1f2017-04-08 19:39:43 +02002352 call setline(1, 'iI')
2353 1normal gUU
2354 call assert_equal("\u0130I", getline(1))
2355 call assert_equal("\u0130I", toupper("iI"))
Bram Moolenaar3317d5e2017-04-08 19:12:06 +02002356
Bram Moolenaar9f4de1f2017-04-08 19:39:43 +02002357 call setline(1, 'iI')
2358 1normal guu
2359 call assert_equal("i\u0131", getline(1))
2360 call assert_equal("i\u0131", tolower("iI"))
Bram Moolenaarf1c118b2018-09-03 22:08:10 +02002361 elseif iupper == "I"
Bram Moolenaar1cc48202017-04-09 13:41:59 +02002362 call setline(1, 'iI')
2363 1normal gUU
2364 call assert_equal("II", getline(1))
2365 call assert_equal("II", toupper("iI"))
2366
2367 call setline(1, 'iI')
2368 1normal guu
2369 call assert_equal("ii", getline(1))
2370 call assert_equal("ii", tolower("iI"))
Bram Moolenaarf1c118b2018-09-03 22:08:10 +02002371 else
2372 call assert_true(false, "expected toupper('i') to be either 'I' or '\u0130'")
2373 endif
2374 set casemap&
2375 call setline(1, 'iI')
2376 1normal gUU
2377 call assert_equal("II", getline(1))
2378 call assert_equal("II", toupper("iI"))
Bram Moolenaar1cc48202017-04-09 13:41:59 +02002379
Bram Moolenaarf1c118b2018-09-03 22:08:10 +02002380 call setline(1, 'iI')
2381 1normal guu
2382 call assert_equal("ii", getline(1))
2383 call assert_equal("ii", tolower("iI"))
2384
2385 lang en_US.UTF-8
2386 catch /E197:/
2387 " can't use Turkish locale
2388 throw 'Skipped: Turkish locale not available'
2389 endtry
Bram Moolenaar1671f442020-03-10 07:48:13 +01002390 close!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002391endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002392
Bram Moolenaar1671f442020-03-10 07:48:13 +01002393" Test for r (replace) command
2394func Test_normal31_r_cmd()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002395 new
2396 call append(0, 'This is a simple test: abcd')
2397 exe "norm! 1gg$r\<cr>"
2398 call assert_equal(['This is a simple test: abc', '', ''], getline(1,'$'))
2399 exe "norm! 1gg2wlr\<cr>"
2400 call assert_equal(['This is a', 'simple test: abc', '', ''], getline(1,'$'))
2401 exe "norm! 2gg0W5r\<cr>"
2402 call assert_equal(['This is a', 'simple ', ' abc', '', ''], getline('1', '$'))
2403 set autoindent
2404 call setline(2, ['simple test: abc', ''])
2405 exe "norm! 2gg0W5r\<cr>"
2406 call assert_equal(['This is a', 'simple ', 'abc', '', '', ''], getline('1', '$'))
2407 exe "norm! 1ggVr\<cr>"
2408 call assert_equal('^M^M^M^M^M^M^M^M^M', strtrans(getline(1)))
2409 call setline(1, 'This is a')
2410 exe "norm! 1gg05rf"
2411 call assert_equal('fffffis a', getline(1))
2412
Bram Moolenaar1671f442020-03-10 07:48:13 +01002413 " When replacing characters, copy characters from above and below lines
2414 " using CTRL-Y and CTRL-E.
2415 " Different code paths are used for utf-8 and latin1 encodings
2416 set showmatch
2417 for enc in ['latin1', 'utf-8']
2418 enew!
2419 let &encoding = enc
2420 call setline(1, [' {a}', 'xxxxxxxxxx', ' [b]'])
2421 exe "norm! 2gg5r\<C-Y>l5r\<C-E>"
2422 call assert_equal(' {a}x [b]x', getline(2))
2423 endfor
2424 set showmatch&
2425
2426 " r command should fail in operator pending mode
2427 call assert_beeps('normal! cr')
2428
Bram Moolenaar004a6782020-04-11 17:09:31 +02002429 " replace a tab character in visual mode
2430 %d
2431 call setline(1, ["a\tb", "c\td", "e\tf"])
2432 normal gglvjjrx
2433 call assert_equal(['axx', 'xxx', 'xxf'], getline(1, '$'))
2434
Bram Moolenaard7e5e942020-10-07 16:54:52 +02002435 " replace with a multibyte character (with multiple composing characters)
2436 %d
2437 new
2438 call setline(1, 'aaa')
2439 exe "normal $ra\u0328\u0301"
2440 call assert_equal("aaa\u0328\u0301", getline(1))
2441
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002442 " clean up
2443 set noautoindent
2444 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002445endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002446
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002447" Test for g*, g#
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01002448func Test_normal32_g_cmd1()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002449 new
2450 call append(0, ['abc.x_foo', 'x_foobar.abc'])
2451 1
2452 norm! $g*
2453 call assert_equal('x_foo', @/)
2454 call assert_equal('x_foobar.abc', getline('.'))
2455 norm! $g#
2456 call assert_equal('abc', @/)
2457 call assert_equal('abc.x_foo', getline('.'))
2458
2459 " clean up
2460 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002461endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002462
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002463" Test for g`, g;, g,, g&, gv, gk, gj, gJ, g0, g^, g_, gm, g$, gM, g CTRL-G,
2464" gi and gI commands
Bram Moolenaar1671f442020-03-10 07:48:13 +01002465func Test_normal33_g_cmd2()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002466 call Setup_NewWindow()
2467 " Test for g`
2468 clearjumps
2469 norm! ma10j
2470 let a=execute(':jumps')
2471 " empty jumplist
2472 call assert_equal('>', a[-1:])
2473 norm! g`a
2474 call assert_equal('>', a[-1:])
2475 call assert_equal(1, line('.'))
2476 call assert_equal('1', getline('.'))
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002477 call cursor(10, 1)
2478 norm! g'a
2479 call assert_equal('>', a[-1:])
2480 call assert_equal(1, line('.'))
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002481
2482 " Test for g; and g,
2483 norm! g;
2484 " there is only one change in the changelist
2485 " currently, when we setup the window
2486 call assert_equal(2, line('.'))
Bram Moolenaare2e40752020-09-04 21:18:46 +02002487 call assert_fails(':norm! g;', 'E662:')
2488 call assert_fails(':norm! g,', 'E663:')
Bram Moolenaar7a1d3282022-06-16 13:04:45 +01002489 let &ul = &ul
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002490 call append('$', ['a', 'b', 'c', 'd'])
Bram Moolenaar7a1d3282022-06-16 13:04:45 +01002491 let &ul = &ul
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002492 call append('$', ['Z', 'Y', 'X', 'W'])
2493 let a = execute(':changes')
2494 call assert_match('2\s\+0\s\+2', a)
2495 call assert_match('101\s\+0\s\+a', a)
2496 call assert_match('105\s\+0\s\+Z', a)
2497 norm! 3g;
2498 call assert_equal(2, line('.'))
2499 norm! 2g,
2500 call assert_equal(105, line('.'))
2501
2502 " Test for g& - global substitute
2503 %d
2504 call setline(1, range(1,10))
2505 call append('$', ['a', 'b', 'c', 'd'])
2506 $s/\w/&&/g
2507 exe "norm! /[1-8]\<cr>"
2508 norm! g&
2509 call assert_equal(['11', '22', '33', '44', '55', '66', '77', '88', '9', '110', 'a', 'b', 'c', 'dd'], getline(1, '$'))
2510
Bram Moolenaar1671f442020-03-10 07:48:13 +01002511 " Jumping to a fold using gg should open the fold
2512 set foldenable
2513 set foldopen+=jump
2514 5,8fold
2515 call feedkeys('6gg', 'xt')
2516 call assert_equal(1, foldlevel('.'))
2517 call assert_equal(-1, foldclosed('.'))
2518 set foldopen-=jump
2519 set foldenable&
2520
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002521 " Test for gv
2522 %d
2523 call append('$', repeat(['abcdefgh'], 8))
2524 exe "norm! 2gg02l\<c-v>2j2ly"
2525 call assert_equal(['cde', 'cde', 'cde'], getreg(0, 1, 1))
2526 " in visual mode, gv swaps current and last selected region
2527 exe "norm! G0\<c-v>4k4lgvd"
2528 call assert_equal(['', 'abfgh', 'abfgh', 'abfgh', 'abcdefgh', 'abcdefgh', 'abcdefgh', 'abcdefgh', 'abcdefgh'], getline(1,'$'))
2529 exe "norm! G0\<c-v>4k4ly"
2530 exe "norm! gvood"
2531 call assert_equal(['', 'abfgh', 'abfgh', 'abfgh', 'fgh', 'fgh', 'fgh', 'fgh', 'fgh'], getline(1,'$'))
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002532 " gv cannot be used in operator pending mode
2533 call assert_beeps('normal! cgv')
2534 " gv should beep without a previously selected visual area
2535 new
2536 call assert_beeps('normal! gv')
2537 close
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002538
2539 " Test for gk/gj
2540 %d
2541 15vsp
2542 set wrap listchars= sbr=
Bram Moolenaar74ede802021-05-29 19:18:01 +02002543 let lineA = 'abcdefghijklmnopqrstuvwxyz'
2544 let lineB = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'
2545 let lineC = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz01234567890123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789'
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002546 $put =lineA
2547 $put =lineB
2548
2549 norm! 3gg0dgk
2550 call assert_equal(['', 'abcdefghijklmno', '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'], getline(1, '$'))
2551 set nu
2552 norm! 3gg0gjdgj
2553 call assert_equal(['', 'abcdefghijklmno', '0123456789AMNOPQRSTUVWXYZ'], getline(1,'$'))
2554
2555 " Test for gJ
2556 norm! 2gggJ
2557 call assert_equal(['', 'abcdefghijklmno0123456789AMNOPQRSTUVWXYZ'], getline(1,'$'))
2558 call assert_equal(16, col('.'))
2559 " shouldn't do anything
2560 norm! 10gJ
2561 call assert_equal(1, col('.'))
2562
2563 " Test for g0 g^ gm g$
2564 exe "norm! 2gg0gji "
2565 call assert_equal(['', 'abcdefghijk lmno0123456789AMNOPQRSTUVWXYZ'], getline(1,'$'))
2566 norm! g0yl
2567 call assert_equal(12, col('.'))
2568 call assert_equal(' ', getreg(0))
2569 norm! g$yl
2570 call assert_equal(22, col('.'))
2571 call assert_equal('3', getreg(0))
2572 norm! gmyl
2573 call assert_equal(17, col('.'))
2574 call assert_equal('n', getreg(0))
2575 norm! g^yl
2576 call assert_equal(15, col('.'))
2577 call assert_equal('l', getreg(0))
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002578 call assert_beeps('normal 5g$')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002579
Bram Moolenaar74ede802021-05-29 19:18:01 +02002580 " Test for g$ with double-width character half displayed
2581 vsplit
2582 9wincmd |
2583 setlocal nowrap nonumber
2584 call setline(2, 'asdfasdf')
2585 2
2586 normal 0g$
2587 call assert_equal(8, col('.'))
2588 10wincmd |
2589 normal 0g$
2590 call assert_equal(9, col('.'))
2591
2592 setlocal signcolumn=yes
2593 11wincmd |
2594 normal 0g$
2595 call assert_equal(8, col('.'))
2596 12wincmd |
2597 normal 0g$
2598 call assert_equal(9, col('.'))
2599
2600 close
2601
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002602 " Test for g_
2603 call assert_beeps('normal! 100g_')
2604 call setline(2, [' foo ', ' foobar '])
2605 normal! 2ggg_
2606 call assert_equal(5, col('.'))
2607 normal! 2g_
2608 call assert_equal(8, col('.'))
2609
2610 norm! 2ggdG
Bram Moolenaar8b530c12019-10-28 02:13:05 +01002611 $put =lineC
2612
2613 " Test for gM
2614 norm! gMyl
2615 call assert_equal(73, col('.'))
2616 call assert_equal('0', getreg(0))
2617 " Test for 20gM
2618 norm! 20gMyl
2619 call assert_equal(29, col('.'))
2620 call assert_equal('S', getreg(0))
2621 " Test for 60gM
2622 norm! 60gMyl
2623 call assert_equal(87, col('.'))
2624 call assert_equal('E', getreg(0))
2625
Bram Moolenaar71c41252021-12-26 15:00:07 +00002626 " Test for gM with Tab characters
2627 call setline('.', "\ta\tb\tc\td\te\tf")
2628 norm! gMyl
2629 call assert_equal(6, col('.'))
2630 call assert_equal("c", getreg(0))
2631
Bram Moolenaar8b530c12019-10-28 02:13:05 +01002632 " Test for g Ctrl-G
Bram Moolenaar71c41252021-12-26 15:00:07 +00002633 call setline('.', lineC)
2634 norm! 60gMyl
Bram Moolenaar8b530c12019-10-28 02:13:05 +01002635 set ff=unix
2636 let a=execute(":norm! g\<c-g>")
2637 call assert_match('Col 87 of 144; Line 2 of 2; Word 1 of 1; Byte 88 of 146', a)
2638
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002639 " Test for gI
2640 norm! gIfoo
Bram Moolenaar8b530c12019-10-28 02:13:05 +01002641 call assert_equal(['', 'foo0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz01234567890123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789'], getline(1,'$'))
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002642
2643 " Test for gi
2644 wincmd c
2645 %d
2646 set tw=0
2647 call setline(1, ['foobar', 'new line'])
2648 norm! A next word
2649 $put ='third line'
2650 norm! gi another word
2651 call assert_equal(['foobar next word another word', 'new line', 'third line'], getline(1,'$'))
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002652 call setline(1, 'foobar')
2653 normal! Ggifirst line
2654 call assert_equal('foobarfirst line', getline(1))
2655 " Test gi in 'virtualedit' mode with cursor after the end of the line
2656 set virtualedit=all
2657 call setline(1, 'foo')
2658 exe "normal! Abar\<Right>\<Right>\<Right>\<Right>"
2659 call setline(1, 'foo')
2660 normal! Ggifirst line
2661 call assert_equal('foo first line', getline(1))
2662 set virtualedit&
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002663
Dominique Pelle923dce22021-11-21 11:36:04 +00002664 " Test for aborting a g command using CTRL-\ CTRL-G
Bram Moolenaar1671f442020-03-10 07:48:13 +01002665 exe "normal! g\<C-\>\<C-G>"
2666 call assert_equal('foo first line', getline('.'))
2667
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002668 " clean up
2669 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002670endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002671
Bram Moolenaarce416b42022-04-03 12:59:34 +01002672func Test_normal_ex_substitute()
2673 " This was hanging on the substitute prompt.
2674 new
2675 call setline(1, 'a')
2676 exe "normal! gggQs/a/b/c\<CR>"
2677 call assert_equal('a', getline(1))
2678 bwipe!
2679endfunc
2680
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002681" Test for g CTRL-G
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01002682func Test_g_ctrl_g()
Bram Moolenaar05295832018-08-24 22:07:58 +02002683 new
2684
2685 let a = execute(":norm! g\<c-g>")
2686 call assert_equal("\n--No lines in buffer--", a)
2687
Bram Moolenaar1671f442020-03-10 07:48:13 +01002688 " Test for CTRL-G (same as :file)
2689 let a = execute(":norm! \<c-g>")
2690 call assert_equal("\n\n\"[No Name]\" --No lines in buffer--", a)
2691
Bram Moolenaar05295832018-08-24 22:07:58 +02002692 call setline(1, ['first line', 'second line'])
2693
2694 " Test g CTRL-g with dos, mac and unix file type.
2695 norm! gojll
2696 set ff=dos
2697 let a = execute(":norm! g\<c-g>")
2698 call assert_equal("\nCol 3 of 11; Line 2 of 2; Word 3 of 4; Byte 15 of 25", a)
2699
2700 set ff=mac
2701 let a = execute(":norm! g\<c-g>")
2702 call assert_equal("\nCol 3 of 11; Line 2 of 2; Word 3 of 4; Byte 14 of 23", a)
2703
2704 set ff=unix
2705 let a = execute(":norm! g\<c-g>")
2706 call assert_equal("\nCol 3 of 11; Line 2 of 2; Word 3 of 4; Byte 14 of 23", a)
2707
2708 " Test g CTRL-g in visual mode (v)
2709 let a = execute(":norm! gojllvlg\<c-g>")
2710 call assert_equal("\nSelected 1 of 2 Lines; 1 of 4 Words; 2 of 23 Bytes", a)
2711
2712 " Test g CTRL-g in visual mode (CTRL-V) with end col > start col
2713 let a = execute(":norm! \<Esc>gojll\<C-V>kllg\<c-g>")
2714 call assert_equal("\nSelected 3 Cols; 2 of 2 Lines; 2 of 4 Words; 6 of 23 Bytes", a)
2715
2716 " Test g_CTRL-g in visual mode (CTRL-V) with end col < start col
2717 let a = execute(":norm! \<Esc>goll\<C-V>jhhg\<c-g>")
2718 call assert_equal("\nSelected 3 Cols; 2 of 2 Lines; 2 of 4 Words; 6 of 23 Bytes", a)
2719
2720 " Test g CTRL-g in visual mode (CTRL-V) with end_vcol being MAXCOL
2721 let a = execute(":norm! \<Esc>gojll\<C-V>k$g\<c-g>")
2722 call assert_equal("\nSelected 2 of 2 Lines; 4 of 4 Words; 17 of 23 Bytes", a)
2723
2724 " There should be one byte less with noeol
2725 set bin noeol
2726 let a = execute(":norm! \<Esc>gog\<c-g>")
2727 call assert_equal("\nCol 1 of 10; Line 1 of 2; Word 1 of 4; Char 1 of 23; Byte 1 of 22", a)
2728 set bin & eol&
2729
Bram Moolenaar30276f22019-01-24 17:59:39 +01002730 call setline(1, ['Français', '日本語'])
Bram Moolenaar05295832018-08-24 22:07:58 +02002731
Bram Moolenaar30276f22019-01-24 17:59:39 +01002732 let a = execute(":norm! \<Esc>gojlg\<c-g>")
2733 call assert_equal("\nCol 4-3 of 9-6; Line 2 of 2; Word 2 of 2; Char 11 of 13; Byte 16 of 20", a)
Bram Moolenaar05295832018-08-24 22:07:58 +02002734
Bram Moolenaar30276f22019-01-24 17:59:39 +01002735 let a = execute(":norm! \<Esc>gojvlg\<c-g>")
2736 call assert_equal("\nSelected 1 of 2 Lines; 1 of 2 Words; 2 of 13 Chars; 6 of 20 Bytes", a)
Bram Moolenaar05295832018-08-24 22:07:58 +02002737
Bram Moolenaar30276f22019-01-24 17:59:39 +01002738 let a = execute(":norm! \<Esc>goll\<c-v>jlg\<c-g>")
2739 call assert_equal("\nSelected 4 Cols; 2 of 2 Lines; 2 of 2 Words; 6 of 13 Chars; 11 of 20 Bytes", a)
Bram Moolenaar05295832018-08-24 22:07:58 +02002740
Bram Moolenaar30276f22019-01-24 17:59:39 +01002741 set fenc=utf8 bomb
2742 let a = execute(":norm! \<Esc>gojlg\<c-g>")
2743 call assert_equal("\nCol 4-3 of 9-6; Line 2 of 2; Word 2 of 2; Char 11 of 13; Byte 16 of 20(+3 for BOM)", a)
Bram Moolenaar05295832018-08-24 22:07:58 +02002744
Bram Moolenaar30276f22019-01-24 17:59:39 +01002745 set fenc=utf16 bomb
2746 let a = execute(":norm! g\<c-g>")
2747 call assert_equal("\nCol 4-3 of 9-6; Line 2 of 2; Word 2 of 2; Char 11 of 13; Byte 16 of 20(+2 for BOM)", a)
Bram Moolenaar05295832018-08-24 22:07:58 +02002748
Bram Moolenaar30276f22019-01-24 17:59:39 +01002749 set fenc=utf32 bomb
2750 let a = execute(":norm! g\<c-g>")
2751 call assert_equal("\nCol 4-3 of 9-6; Line 2 of 2; Word 2 of 2; Char 11 of 13; Byte 16 of 20(+4 for BOM)", a)
Bram Moolenaar05295832018-08-24 22:07:58 +02002752
Bram Moolenaar30276f22019-01-24 17:59:39 +01002753 set fenc& bomb&
Bram Moolenaar05295832018-08-24 22:07:58 +02002754
2755 set ff&
2756 bwipe!
2757endfunc
2758
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002759" Test for g8
Bram Moolenaar1671f442020-03-10 07:48:13 +01002760func Test_normal34_g_cmd3()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002761 new
Bram Moolenaar395b6ba2017-04-07 20:09:51 +02002762 let a=execute(':norm! 1G0g8')
2763 call assert_equal("\nNUL", a)
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002764
Bram Moolenaar395b6ba2017-04-07 20:09:51 +02002765 call setline(1, 'abcdefghijklmnopqrstuvwxyzäüö')
2766 let a=execute(':norm! 1G$g8')
2767 call assert_equal("\nc3 b6 ", a)
2768
2769 call setline(1, "a\u0302")
2770 let a=execute(':norm! 1G0g8')
2771 call assert_equal("\n61 + cc 82 ", a)
2772
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002773 " clean up
2774 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002775endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002776
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002777" Test 8g8 which finds invalid utf8 at or after the cursor.
Bram Moolenaar395b6ba2017-04-07 20:09:51 +02002778func Test_normal_8g8()
Bram Moolenaar395b6ba2017-04-07 20:09:51 +02002779 new
2780
Bram Moolenaar395b6ba2017-04-07 20:09:51 +02002781 " With invalid byte.
2782 call setline(1, "___\xff___")
2783 norm! 1G08g8g
2784 call assert_equal([0, 1, 4, 0, 1], getcurpos())
2785
2786 " With invalid byte before the cursor.
2787 call setline(1, "___\xff___")
2788 norm! 1G$h8g8g
2789 call assert_equal([0, 1, 6, 0, 9], getcurpos())
2790
2791 " With truncated sequence.
2792 call setline(1, "___\xE2\x82___")
2793 norm! 1G08g8g
2794 call assert_equal([0, 1, 4, 0, 1], getcurpos())
2795
2796 " With overlong sequence.
2797 call setline(1, "___\xF0\x82\x82\xAC___")
2798 norm! 1G08g8g
2799 call assert_equal([0, 1, 4, 0, 1], getcurpos())
2800
2801 " With valid utf8.
2802 call setline(1, "café")
2803 norm! 1G08g8
2804 call assert_equal([0, 1, 1, 0, 1], getcurpos())
2805
2806 bw!
2807endfunc
2808
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002809" Test for g<
Bram Moolenaar1671f442020-03-10 07:48:13 +01002810func Test_normal35_g_cmd4()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002811 " Cannot capture its output,
2812 " probably a bug, therefore, test disabled:
Bram Moolenaar31845092016-09-05 22:58:31 +02002813 throw "Skipped: output of g< can't be tested currently"
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002814 echo "a\nb\nc\nd"
2815 let b=execute(':norm! g<')
2816 call assert_true(!empty(b), 'failed `execute(g<)`')
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002817endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002818
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002819" Test for gp gP go
Bram Moolenaar1671f442020-03-10 07:48:13 +01002820func Test_normal36_g_cmd5()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002821 new
2822 call append(0, 'abcdefghijklmnopqrstuvwxyz')
Bram Moolenaar0913a102016-09-03 19:11:59 +02002823 set ff=unix
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002824 " Test for gp gP
2825 call append(1, range(1,10))
2826 1
2827 norm! 1yy
2828 3
2829 norm! gp
2830 call assert_equal([0, 5, 1, 0, 1], getcurpos())
2831 $
2832 norm! gP
2833 call assert_equal([0, 14, 1, 0, 1], getcurpos())
2834
2835 " Test for go
2836 norm! 26go
2837 call assert_equal([0, 1, 26, 0, 26], getcurpos())
2838 norm! 27go
2839 call assert_equal([0, 1, 26, 0, 26], getcurpos())
2840 norm! 28go
2841 call assert_equal([0, 2, 1, 0, 1], getcurpos())
2842 set ff=dos
2843 norm! 29go
2844 call assert_equal([0, 2, 1, 0, 1], getcurpos())
2845 set ff=unix
2846 norm! gg0
2847 norm! 101go
2848 call assert_equal([0, 13, 26, 0, 26], getcurpos())
2849 norm! 103go
2850 call assert_equal([0, 14, 1, 0, 1], getcurpos())
2851 " count > buffer content
2852 norm! 120go
naohiro ono56200ee2022-01-01 14:59:44 +00002853 call assert_equal([0, 14, 1, 0, v:maxcol], getcurpos())
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002854 " clean up
2855 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002856endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002857
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002858" Test for gt and gT
Bram Moolenaar1671f442020-03-10 07:48:13 +01002859func Test_normal37_g_cmd6()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002860 tabnew 1.txt
2861 tabnew 2.txt
2862 tabnew 3.txt
2863 norm! 1gt
2864 call assert_equal(1, tabpagenr())
2865 norm! 3gt
2866 call assert_equal(3, tabpagenr())
2867 norm! 1gT
2868 " count gT goes not to the absolute tabpagenumber
2869 " but, but goes to the count previous tabpagenumber
2870 call assert_equal(2, tabpagenr())
2871 " wrap around
2872 norm! 3gT
2873 call assert_equal(3, tabpagenr())
2874 " gt does not wrap around
2875 norm! 5gt
2876 call assert_equal(3, tabpagenr())
2877
2878 for i in range(3)
2879 tabclose
2880 endfor
2881 " clean up
Bram Moolenaarbc2b71d2020-02-17 21:33:30 +01002882 call assert_fails(':tabclose', 'E784:')
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002883endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002884
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002885" Test for <Home> and <C-Home> key
Bram Moolenaar1671f442020-03-10 07:48:13 +01002886func Test_normal38_nvhome()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002887 new
2888 call setline(1, range(10))
2889 $
2890 setl et sw=2
2891 norm! V10>$
2892 " count is ignored
2893 exe "norm! 10\<home>"
2894 call assert_equal(1, col('.'))
2895 exe "norm! \<home>"
2896 call assert_equal([0, 10, 1, 0, 1], getcurpos())
2897 exe "norm! 5\<c-home>"
2898 call assert_equal([0, 5, 1, 0, 1], getcurpos())
2899 exe "norm! \<c-home>"
2900 call assert_equal([0, 1, 1, 0, 1], getcurpos())
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002901 exe "norm! G\<c-kHome>"
2902 call assert_equal([0, 1, 1, 0, 1], getcurpos())
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002903
2904 " clean up
2905 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002906endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002907
Bram Moolenaar1671f442020-03-10 07:48:13 +01002908" Test for <End> and <C-End> keys
2909func Test_normal_nvend()
2910 new
2911 call setline(1, map(range(1, 10), '"line" .. v:val'))
2912 exe "normal! \<End>"
2913 call assert_equal(5, col('.'))
2914 exe "normal! 4\<End>"
2915 call assert_equal([4, 5], [line('.'), col('.')])
2916 exe "normal! \<C-End>"
2917 call assert_equal([10, 6], [line('.'), col('.')])
2918 close!
2919endfunc
2920
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002921" Test for cw cW ce
Bram Moolenaar1671f442020-03-10 07:48:13 +01002922func Test_normal39_cw()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002923 " Test for cw and cW on whitespace
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002924 new
2925 set tw=0
2926 call append(0, 'here are some words')
2927 norm! 1gg0elcwZZZ
2928 call assert_equal('hereZZZare some words', getline('.'))
2929 norm! 1gg0elcWYYY
2930 call assert_equal('hereZZZareYYYsome words', getline('.'))
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002931 norm! 2gg0cwfoo
2932 call assert_equal('foo', getline('.'))
2933
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002934 call setline(1, 'one; two')
2935 call cursor(1, 1)
2936 call feedkeys('cwvim', 'xt')
2937 call assert_equal('vim; two', getline(1))
2938 call feedkeys('0cWone', 'xt')
2939 call assert_equal('one two', getline(1))
2940 "When cursor is at the end of a word 'ce' will change until the end of the
2941 "next word, but 'cw' will change only one character
2942 call setline(1, 'one two')
2943 call feedkeys('0ecwce', 'xt')
2944 call assert_equal('once two', getline(1))
2945 call setline(1, 'one two')
2946 call feedkeys('0ecely', 'xt')
2947 call assert_equal('only', getline(1))
2948
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002949 " clean up
2950 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002951endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002952
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002953" Test for CTRL-\ commands
Bram Moolenaar1671f442020-03-10 07:48:13 +01002954func Test_normal40_ctrl_bsl()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002955 new
2956 call append(0, 'here are some words')
2957 exe "norm! 1gg0a\<C-\>\<C-N>"
2958 call assert_equal('n', mode())
2959 call assert_equal(1, col('.'))
2960 call assert_equal('', visualmode())
2961 exe "norm! 1gg0viw\<C-\>\<C-N>"
2962 call assert_equal('n', mode())
2963 call assert_equal(4, col('.'))
2964 exe "norm! 1gg0a\<C-\>\<C-G>"
2965 call assert_equal('n', mode())
2966 call assert_equal(1, col('.'))
2967 "imap <buffer> , <c-\><c-n>
2968 set im
2969 exe ":norm! \<c-\>\<c-n>dw"
2970 set noim
2971 call assert_equal('are some words', getline(1))
2972 call assert_false(&insertmode)
Yegappan Lakshmanan1a71d312021-07-15 12:49:58 +02002973 call assert_beeps("normal! \<C-\>\<C-A>")
Bram Moolenaar1671f442020-03-10 07:48:13 +01002974
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002975 " clean up
2976 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002977endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002978
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002979" Test for <c-r>=, <c-r><c-r>= and <c-r><c-o>= in insert mode
Bram Moolenaar1671f442020-03-10 07:48:13 +01002980func Test_normal41_insert_reg()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002981 new
2982 set sts=2 sw=2 ts=8 tw=0
2983 call append(0, ["aaa\tbbb\tccc", '', '', ''])
2984 let a=getline(1)
2985 norm! 2gg0
2986 exe "norm! a\<c-r>=a\<cr>"
2987 norm! 3gg0
2988 exe "norm! a\<c-r>\<c-r>=a\<cr>"
2989 norm! 4gg0
2990 exe "norm! a\<c-r>\<c-o>=a\<cr>"
2991 call assert_equal(['aaa bbb ccc', 'aaa bbb ccc', 'aaa bbb ccc', 'aaa bbb ccc', ''], getline(1, '$'))
2992
2993 " clean up
2994 set sts=0 sw=8 ts=8
Bram Moolenaar31845092016-09-05 22:58:31 +02002995 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02002996endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02002997
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01002998" Test for Ctrl-D and Ctrl-U
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01002999func Test_normal42_halfpage()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02003000 call Setup_NewWindow()
3001 call assert_equal(5, &scroll)
3002 exe "norm! \<c-d>"
3003 call assert_equal('6', getline('.'))
3004 exe "norm! 2\<c-d>"
3005 call assert_equal('8', getline('.'))
3006 call assert_equal(2, &scroll)
3007 set scroll=5
3008 exe "norm! \<c-u>"
3009 call assert_equal('3', getline('.'))
3010 1
3011 set scrolloff=5
3012 exe "norm! \<c-d>"
3013 call assert_equal('10', getline('.'))
3014 exe "norm! \<c-u>"
3015 call assert_equal('5', getline('.'))
3016 1
3017 set scrolloff=99
3018 exe "norm! \<c-d>"
3019 call assert_equal('10', getline('.'))
3020 set scrolloff=0
3021 100
3022 exe "norm! $\<c-u>"
3023 call assert_equal('95', getline('.'))
3024 call assert_equal([0, 95, 1, 0, 1], getcurpos())
3025 100
3026 set nostartofline
3027 exe "norm! $\<c-u>"
3028 call assert_equal('95', getline('.'))
naohiro ono56200ee2022-01-01 14:59:44 +00003029 call assert_equal([0, 95, 2, 0, v:maxcol], getcurpos())
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02003030 " cleanup
3031 set startofline
3032 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003033endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02003034
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003035func Test_normal45_drop()
Bram Moolenaar29495952018-02-12 22:49:00 +01003036 if !has('dnd')
Bram Moolenaarb48e96f2018-02-13 12:26:14 +01003037 " The ~ register does not exist
3038 call assert_beeps('norm! "~')
Bram Moolenaar29495952018-02-12 22:49:00 +01003039 return
3040 endif
3041
3042 " basic test for drag-n-drop
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02003043 " unfortunately, without a gui, we can't really test much here,
3044 " so simply test that ~p fails (which uses the drop register)
3045 new
Bram Moolenaare2e40752020-09-04 21:18:46 +02003046 call assert_fails(':norm! "~p', 'E353:')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02003047 call assert_equal([], getreg('~', 1, 1))
3048 " the ~ register is read only
Bram Moolenaare2e40752020-09-04 21:18:46 +02003049 call assert_fails(':let @~="1"', 'E354:')
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02003050 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003051endfunc
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02003052
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003053func Test_normal46_ignore()
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02003054 new
3055 " How to test this?
3056 " let's just for now test, that the buffer
3057 " does not change
3058 call feedkeys("\<c-s>", 't')
3059 call assert_equal([''], getline(1,'$'))
3060
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003061 " no valid commands
3062 exe "norm! \<char-0x100>"
3063 call assert_equal([''], getline(1,'$'))
3064
3065 exe "norm! ä"
3066 call assert_equal([''], getline(1,'$'))
3067
Bram Moolenaar87bc3f72016-09-03 17:33:54 +02003068 " clean up
3069 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003070endfunc
Bram Moolenaarc4a908e2016-09-08 23:35:30 +02003071
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003072func Test_normal47_visual_buf_wipe()
Bram Moolenaarc4a908e2016-09-08 23:35:30 +02003073 " This was causing a crash or ml_get error.
3074 enew!
3075 call setline(1,'xxx')
3076 normal $
3077 new
3078 call setline(1, range(1,2))
3079 2
3080 exe "norm \<C-V>$"
3081 bw!
3082 norm yp
3083 set nomodified
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003084endfunc
3085
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003086func Test_normal48_wincmd()
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003087 new
3088 exe "norm! \<c-w>c"
3089 call assert_equal(1, winnr('$'))
Bram Moolenaare2e40752020-09-04 21:18:46 +02003090 call assert_fails(":norm! \<c-w>c", 'E444:')
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003091endfunc
3092
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003093func Test_normal49_counts()
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003094 new
3095 call setline(1, 'one two three four five six seven eight nine ten')
3096 1
3097 norm! 3d2w
3098 call assert_equal('seven eight nine ten', getline(1))
3099 bw!
3100endfunc
3101
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003102func Test_normal50_commandline()
Bram Moolenaar004a6782020-04-11 17:09:31 +02003103 CheckFeature timers
3104 CheckFeature cmdline_hist
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003105 func! DoTimerWork(id)
3106 call assert_equal('[Command Line]', bufname(''))
3107 " should fail, with E11, but does fail with E23?
3108 "call feedkeys("\<c-^>", 'tm')
3109
3110 " should also fail with E11
Bram Moolenaare2e40752020-09-04 21:18:46 +02003111 call assert_fails(":wincmd p", 'E11:')
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003112 " return from commandline window
3113 call feedkeys("\<cr>")
3114 endfunc
3115
3116 let oldlang=v:lang
3117 lang C
3118 set updatetime=20
3119 call timer_start(100, 'DoTimerWork')
3120 try
3121 " throws E23, for whatever reason...
3122 call feedkeys('q:', 'x!')
3123 catch /E23/
3124 " no-op
3125 endtry
3126 " clean up
3127 set updatetime=4000
3128 exe "lang" oldlang
3129 bw!
3130endfunc
3131
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003132func Test_normal51_FileChangedRO()
Bram Moolenaar004a6782020-04-11 17:09:31 +02003133 CheckFeature autocmd
Bram Moolenaare5f2a072017-02-01 22:31:49 +01003134 " Don't sleep after the warning message.
3135 call test_settime(1)
Bram Moolenaarb152b6a2022-09-29 21:37:33 +01003136 call writefile(['foo'], 'Xreadonly.log', 'D')
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003137 new Xreadonly.log
3138 setl ro
3139 au FileChangedRO <buffer> :call feedkeys("\<c-^>", 'tix')
Bram Moolenaare2e40752020-09-04 21:18:46 +02003140 call assert_fails(":norm! Af", 'E788:')
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003141 call assert_equal(['foo'], getline(1,'$'))
3142 call assert_equal('Xreadonly.log', bufname(''))
3143
3144 " cleanup
Bram Moolenaare5f2a072017-02-01 22:31:49 +01003145 call test_settime(0)
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003146 bw!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003147endfunc
3148
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003149func Test_normal52_rl()
Bram Moolenaar004a6782020-04-11 17:09:31 +02003150 CheckFeature rightleft
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003151 new
3152 call setline(1, 'abcde fghij klmnopq')
3153 norm! 1gg$
3154 set rl
3155 call assert_equal(19, col('.'))
3156 call feedkeys('l', 'tx')
3157 call assert_equal(18, col('.'))
3158 call feedkeys('h', 'tx')
3159 call assert_equal(19, col('.'))
3160 call feedkeys("\<right>", 'tx')
3161 call assert_equal(18, col('.'))
Bram Moolenaar1671f442020-03-10 07:48:13 +01003162 call feedkeys("\<left>", 'tx')
3163 call assert_equal(19, col('.'))
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003164 call feedkeys("\<s-right>", 'tx')
3165 call assert_equal(13, col('.'))
3166 call feedkeys("\<c-right>", 'tx')
3167 call assert_equal(7, col('.'))
3168 call feedkeys("\<c-left>", 'tx')
3169 call assert_equal(13, col('.'))
3170 call feedkeys("\<s-left>", 'tx')
3171 call assert_equal(19, col('.'))
3172 call feedkeys("<<", 'tx')
3173 call assert_equal(' abcde fghij klmnopq',getline(1))
3174 call feedkeys(">>", 'tx')
3175 call assert_equal('abcde fghij klmnopq',getline(1))
3176
3177 " cleanup
3178 set norl
3179 bw!
3180endfunc
3181
Bram Moolenaarb1e04fc2017-03-29 13:08:35 +02003182func Test_normal54_Ctrl_bsl()
3183 new
3184 call setline(1, 'abcdefghijklmn')
3185 exe "norm! df\<c-\>\<c-n>"
3186 call assert_equal(['abcdefghijklmn'], getline(1,'$'))
3187 exe "norm! df\<c-\>\<c-g>"
3188 call assert_equal(['abcdefghijklmn'], getline(1,'$'))
3189 exe "norm! df\<c-\>m"
3190 call assert_equal(['abcdefghijklmn'], getline(1,'$'))
Bram Moolenaar30276f22019-01-24 17:59:39 +01003191
Bram Moolenaarb1e04fc2017-03-29 13:08:35 +02003192 call setline(2, 'abcdefghijklmnāf')
3193 norm! 2gg0
3194 exe "norm! df\<Char-0x101>"
3195 call assert_equal(['abcdefghijklmn', 'f'], getline(1,'$'))
3196 norm! 1gg0
3197 exe "norm! df\<esc>"
3198 call assert_equal(['abcdefghijklmn', 'f'], getline(1,'$'))
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003199
Bram Moolenaarb1e04fc2017-03-29 13:08:35 +02003200 " clean up
3201 bw!
3202endfunc
3203
3204func Test_normal_large_count()
3205 " This may fail with 32bit long, how do we detect that?
3206 new
3207 normal o
3208 normal 6666666666dL
3209 bwipe!
Bram Moolenaar2931f2a2016-09-09 16:59:08 +02003210endfunc
Bram Moolenaarbf3d5802017-03-29 19:48:11 +02003211
3212func Test_delete_until_paragraph()
Bram Moolenaarbf3d5802017-03-29 19:48:11 +02003213 new
3214 normal grádv}
3215 call assert_equal('á', getline(1))
3216 normal grád}
3217 call assert_equal('', getline(1))
3218 bwipe!
3219endfunc
Bram Moolenaarfb094e12017-11-05 20:59:28 +01003220
3221" Test for the gr (virtual replace) command
3222" Test for the bug fixed by 7.4.387
3223func Test_gr_command()
3224 enew!
3225 let save_cpo = &cpo
3226 call append(0, ['First line', 'Second line', 'Third line'])
3227 exe "normal i\<C-G>u"
3228 call cursor(2, 1)
3229 set cpo-=X
3230 normal 4gro
3231 call assert_equal('oooond line', getline(2))
3232 undo
3233 set cpo+=X
3234 normal 4gro
3235 call assert_equal('ooooecond line', getline(2))
3236 let &cpo = save_cpo
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003237 normal! ggvegrx
3238 call assert_equal('xxxxx line', getline(1))
3239 exe "normal! gggr\<C-V>122"
3240 call assert_equal('zxxxx line', getline(1))
3241 set virtualedit=all
3242 normal! 15|grl
3243 call assert_equal('zxxxx line l', getline(1))
3244 set virtualedit&
3245 set nomodifiable
3246 call assert_fails('normal! grx', 'E21:')
3247 call assert_fails('normal! gRx', 'E21:')
3248 set modifiable&
Bram Moolenaarfb094e12017-11-05 20:59:28 +01003249 enew!
3250endfunc
3251
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003252func Test_nv_hat_count()
3253 %bwipeout!
3254 let l:nr = bufnr('%') + 1
Bram Moolenaare2e40752020-09-04 21:18:46 +02003255 call assert_fails(':execute "normal! ' . l:nr . '\<C-^>"', 'E92:')
Bram Moolenaar1bbb6192018-11-10 16:02:01 +01003256
3257 edit Xfoo
3258 let l:foo_nr = bufnr('Xfoo')
3259
3260 edit Xbar
3261 let l:bar_nr = bufnr('Xbar')
3262
3263 " Make sure we are not just using the alternate file.
3264 edit Xbaz
3265
3266 call feedkeys(l:foo_nr . "\<C-^>", 'tx')
3267 call assert_equal('Xfoo', fnamemodify(bufname('%'), ':t'))
3268
3269 call feedkeys(l:bar_nr . "\<C-^>", 'tx')
3270 call assert_equal('Xbar', fnamemodify(bufname('%'), ':t'))
3271
3272 %bwipeout!
3273endfunc
Bram Moolenaara84a3dd2019-03-25 22:21:24 +01003274
3275func Test_message_when_using_ctrl_c()
Bram Moolenaar553e5a52019-03-25 23:16:34 +01003276 " Make sure no buffers are changed.
3277 %bwipe!
3278
Bram Moolenaara84a3dd2019-03-25 22:21:24 +01003279 exe "normal \<C-C>"
3280 call assert_match("Type :qa and press <Enter> to exit Vim", Screenline(&lines))
Bram Moolenaar553e5a52019-03-25 23:16:34 +01003281
Bram Moolenaara84a3dd2019-03-25 22:21:24 +01003282 new
3283 cal setline(1, 'hi!')
3284 exe "normal \<C-C>"
3285 call assert_match("Type :qa! and press <Enter> to abandon all changes and exit Vim", Screenline(&lines))
Bram Moolenaar553e5a52019-03-25 23:16:34 +01003286
Bram Moolenaara84a3dd2019-03-25 22:21:24 +01003287 bwipe!
3288endfunc
Bram Moolenaarc6b37db2019-04-27 18:00:34 +02003289
Bram Moolenaar7a1d3282022-06-16 13:04:45 +01003290func Test_mode_updated_after_ctrl_c()
3291 CheckScreendump
3292
3293 let buf = RunVimInTerminal('', {'rows': 5})
3294 call term_sendkeys(buf, "i")
3295 call term_sendkeys(buf, "\<C-O>")
3296 " wait a moment so that the "-- (insert) --" message is displayed
3297 call TermWait(buf, 50)
3298 call term_sendkeys(buf, "\<C-C>")
3299 call VerifyScreenDump(buf, 'Test_mode_updated_1', {})
3300
3301 call StopVimInTerminal(buf)
3302endfunc
3303
Bram Moolenaarc6b37db2019-04-27 18:00:34 +02003304" Test for '[m', ']m', '[M' and ']M'
3305" Jumping to beginning and end of methods in Java-like languages
3306func Test_java_motion()
3307 new
Bram Moolenaar1671f442020-03-10 07:48:13 +01003308 call assert_beeps('normal! [m')
3309 call assert_beeps('normal! ]m')
3310 call assert_beeps('normal! [M')
3311 call assert_beeps('normal! ]M')
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02003312 let lines =<< trim [CODE]
3313 Piece of Java
3314 {
3315 tt m1 {
3316 t1;
3317 } e1
Bram Moolenaarc6b37db2019-04-27 18:00:34 +02003318
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02003319 tt m2 {
3320 t2;
3321 } e2
Bram Moolenaarc6b37db2019-04-27 18:00:34 +02003322
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02003323 tt m3 {
3324 if (x)
3325 {
3326 t3;
3327 }
3328 } e3
3329 }
3330 [CODE]
3331 call setline(1, lines)
Bram Moolenaarc6b37db2019-04-27 18:00:34 +02003332
3333 normal gg
3334
3335 normal 2]maA
3336 call assert_equal("\ttt m1 {A", getline('.'))
3337 call assert_equal([3, 9, 16], [line('.'), col('.'), virtcol('.')])
3338
3339 normal j]maB
3340 call assert_equal("\ttt m2 {B", getline('.'))
3341 call assert_equal([7, 9, 16], [line('.'), col('.'), virtcol('.')])
3342
3343 normal ]maC
3344 call assert_equal("\ttt m3 {C", getline('.'))
3345 call assert_equal([11, 9, 16], [line('.'), col('.'), virtcol('.')])
3346
3347 normal [maD
3348 call assert_equal("\ttt m3 {DC", getline('.'))
3349 call assert_equal([11, 9, 16], [line('.'), col('.'), virtcol('.')])
3350
3351 normal k2[maE
3352 call assert_equal("\ttt m1 {EA", getline('.'))
3353 call assert_equal([3, 9, 16], [line('.'), col('.'), virtcol('.')])
3354
3355 normal 3[maF
3356 call assert_equal("{F", getline('.'))
3357 call assert_equal([2, 2, 2], [line('.'), col('.'), virtcol('.')])
3358
3359 normal ]MaG
3360 call assert_equal("\t}G e1", getline('.'))
3361 call assert_equal([5, 3, 10], [line('.'), col('.'), virtcol('.')])
3362
3363 normal j2]MaH
3364 call assert_equal("\t}H e3", getline('.'))
3365 call assert_equal([16, 3, 10], [line('.'), col('.'), virtcol('.')])
3366
3367 normal ]M]M
3368 normal aI
3369 call assert_equal("}I", getline('.'))
3370 call assert_equal([17, 2, 2], [line('.'), col('.'), virtcol('.')])
3371
3372 normal 2[MaJ
3373 call assert_equal("\t}JH e3", getline('.'))
3374 call assert_equal([16, 3, 10], [line('.'), col('.'), virtcol('.')])
3375
3376 normal k[MaK
3377 call assert_equal("\t}K e2", getline('.'))
3378 call assert_equal([9, 3, 10], [line('.'), col('.'), virtcol('.')])
3379
3380 normal 3[MaL
3381 call assert_equal("{LF", getline('.'))
3382 call assert_equal([2, 2, 2], [line('.'), col('.'), virtcol('.')])
3383
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02003384 call cursor(2, 1)
3385 call assert_beeps('norm! 5]m')
3386
3387 " jumping to a method in a fold should open the fold
3388 6,10fold
3389 call feedkeys("gg3]m", 'xt')
3390 call assert_equal([7, 8, 15], [line('.'), col('.'), virtcol('.')])
3391 call assert_equal(-1, foldclosedend(7))
3392
Bram Moolenaarc6b37db2019-04-27 18:00:34 +02003393 close!
3394endfunc
Bram Moolenaard5c82342019-07-27 18:44:57 +02003395
Bram Moolenaar004a6782020-04-11 17:09:31 +02003396" Tests for g cmds
Bram Moolenaar1671f442020-03-10 07:48:13 +01003397func Test_normal_gdollar_cmd()
Bram Moolenaard5c82342019-07-27 18:44:57 +02003398 call Setup_NewWindow()
3399 " Make long lines that will wrap
3400 %s/$/\=repeat(' foobar', 10)/
3401 20vsp
3402 set wrap
3403 " Test for g$ with count
3404 norm! gg
3405 norm! 0vg$y
3406 call assert_equal(20, col("'>"))
3407 call assert_equal('1 foobar foobar foob', getreg(0))
3408 norm! gg
3409 norm! 0v4g$y
3410 call assert_equal(72, col("'>"))
3411 call assert_equal('1 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.."\n", getreg(0))
3412 norm! gg
3413 norm! 0v6g$y
3414 call assert_equal(40, col("'>"))
3415 call assert_equal('1 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.. "\n"..
3416 \ '2 foobar foobar foobar foobar foobar foo', getreg(0))
3417 set nowrap
3418 " clean up
3419 norm! gg
3420 norm! 0vg$y
3421 call assert_equal(20, col("'>"))
3422 call assert_equal('1 foobar foobar foob', getreg(0))
3423 norm! gg
3424 norm! 0v4g$y
3425 call assert_equal(20, col("'>"))
3426 call assert_equal('1 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.. "\n"..
3427 \ '2 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.. "\n"..
3428 \ '3 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.. "\n"..
3429 \ '4 foobar foobar foob', getreg(0))
3430 norm! gg
3431 norm! 0v6g$y
3432 call assert_equal(20, col("'>"))
3433 call assert_equal('1 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.. "\n"..
3434 \ '2 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.. "\n"..
3435 \ '3 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.. "\n"..
3436 \ '4 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.. "\n"..
3437 \ '5 foobar foobar foobar foobar foobar foobar foobar foobar foobar foobar'.. "\n"..
3438 \ '6 foobar foobar foob', getreg(0))
3439 " Move to last line, also down movement is not possible, should still move
3440 " the cursor to the last visible char
3441 norm! G
3442 norm! 0v6g$y
3443 call assert_equal(20, col("'>"))
3444 call assert_equal('100 foobar foobar fo', getreg(0))
3445 bw!
3446endfunc
Bram Moolenaar03ac52f2019-09-24 22:47:46 +02003447
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003448func Test_normal_gk_gj()
Bram Moolenaar03ac52f2019-09-24 22:47:46 +02003449 " needs 80 column new window
3450 new
3451 vert 80new
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003452 call assert_beeps('normal gk')
Bram Moolenaar03ac52f2019-09-24 22:47:46 +02003453 put =[repeat('x',90)..' {{{1', 'x {{{1']
3454 norm! gk
3455 " In a 80 column wide terminal the window will be only 78 char
3456 " (because Vim will leave space for the other window),
3457 " but if the terminal is larger, it will be 80 chars, so verify the
3458 " cursor column correctly.
3459 call assert_equal(winwidth(0)+1, col('.'))
3460 call assert_equal(winwidth(0)+1, virtcol('.'))
3461 norm! j
3462 call assert_equal(6, col('.'))
3463 call assert_equal(6, virtcol('.'))
3464 norm! gk
3465 call assert_equal(95, col('.'))
3466 call assert_equal(95, virtcol('.'))
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003467 %bw!
Bram Moolenaarceba3dd2019-10-12 16:12:54 +02003468
3469 " needs 80 column new window
3470 new
3471 vert 80new
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003472 call assert_beeps('normal gj')
Bram Moolenaarceba3dd2019-10-12 16:12:54 +02003473 set number
3474 set numberwidth=10
3475 set cpoptions+=n
3476 put =[repeat('0',90), repeat('1',90)]
3477 norm! 075l
3478 call assert_equal(76, col('.'))
3479 norm! gk
3480 call assert_equal(1, col('.'))
3481 norm! gk
3482 call assert_equal(76, col('.'))
3483 norm! gk
3484 call assert_equal(1, col('.'))
3485 norm! gj
3486 call assert_equal(76, col('.'))
3487 norm! gj
3488 call assert_equal(1, col('.'))
3489 norm! gj
3490 call assert_equal(76, col('.'))
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003491 " When 'nowrap' is set, gk and gj behave like k and j
3492 set nowrap
3493 normal! gk
3494 call assert_equal([2, 76], [line('.'), col('.')])
3495 normal! gj
3496 call assert_equal([3, 76], [line('.'), col('.')])
3497 %bw!
3498 set cpoptions& number& numberwidth& wrap&
Bram Moolenaar03ac52f2019-09-24 22:47:46 +02003499endfunc
Bram Moolenaarf0cee192020-02-16 13:33:56 +01003500
Bram Moolenaar818fc9a2020-02-21 17:54:45 +01003501" Test for using : to run a multi-line Ex command in operator pending mode
3502func Test_normal_yank_with_excmd()
3503 new
3504 call setline(1, ['foo', 'bar', 'baz'])
3505 let @a = ''
3506 call feedkeys("\"ay:if v:true\<CR>normal l\<CR>endif\<CR>", 'xt')
3507 call assert_equal('f', @a)
3508 close!
3509endfunc
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003510
3511" Test for supplying a count to a normal-mode command across a cursorhold call
3512func Test_normal_cursorhold_with_count()
3513 func s:cHold()
3514 let g:cHold_Called += 1
3515 endfunc
3516 new
3517 augroup normalcHoldTest
3518 au!
3519 au CursorHold <buffer> call s:cHold()
3520 augroup END
3521 let g:cHold_Called = 0
3522 call feedkeys("3\<CursorHold>2ix", 'xt')
3523 call assert_equal(1, g:cHold_Called)
3524 call assert_equal(repeat('x', 32), getline(1))
3525 augroup normalcHoldTest
3526 au!
3527 augroup END
3528 au! normalcHoldTest
3529 close!
3530 delfunc s:cHold
3531endfunc
3532
3533" Test for using a count and a command with CTRL-W
3534func Test_wincmd_with_count()
3535 call feedkeys("\<C-W>12n", 'xt')
3536 call assert_equal(12, winheight(0))
3537endfunc
3538
3539" Test for 'b', 'B' 'ge' and 'gE' commands
Bram Moolenaar1671f442020-03-10 07:48:13 +01003540func Test_horiz_motion()
3541 new
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003542 normal! gg
3543 call assert_beeps('normal! b')
3544 call assert_beeps('normal! B')
3545 call assert_beeps('normal! gE')
3546 call assert_beeps('normal! ge')
Bram Moolenaar1671f442020-03-10 07:48:13 +01003547 " <S-Backspace> moves one word left and <C-Backspace> moves one WORD left
3548 call setline(1, 'one ,two ,three')
3549 exe "normal! $\<S-BS>"
3550 call assert_equal(11, col('.'))
3551 exe "normal! $\<C-BS>"
3552 call assert_equal(10, col('.'))
3553 close!
3554endfunc
3555
3556" Test for using a : command in operator pending mode
3557func Test_normal_colon_op()
3558 new
3559 call setline(1, ['one', 'two'])
3560 call assert_beeps("normal! Gc:d\<CR>")
3561 close!
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003562endfunc
3563
Bram Moolenaar004a6782020-04-11 17:09:31 +02003564" Test for d and D commands
3565func Test_normal_delete_cmd()
3566 new
3567 " D in an empty line
3568 call setline(1, '')
3569 normal D
3570 call assert_equal('', getline(1))
3571 " D in an empty line in virtualedit mode
3572 set virtualedit=all
3573 normal D
3574 call assert_equal('', getline(1))
3575 set virtualedit&
3576 " delete to a readonly register
3577 call setline(1, ['abcd'])
3578 call assert_beeps('normal ":d2l')
Bram Moolenaar6fd367a2021-03-13 13:14:04 +01003579
3580 " D and d with 'nomodifiable'
3581 call setline(1, ['abcd'])
3582 setlocal nomodifiable
3583 call assert_fails('normal D', 'E21:')
3584 call assert_fails('normal d$', 'E21:')
3585
Bram Moolenaar004a6782020-04-11 17:09:31 +02003586 close!
3587endfunc
3588
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02003589" Test for deleting or changing characters across lines with 'whichwrap'
3590" containing 's'. Should count <EOL> as one character.
3591func Test_normal_op_across_lines()
3592 new
3593 set whichwrap&
3594 call setline(1, ['one two', 'three four'])
3595 exe "norm! $3d\<Space>"
3596 call assert_equal(['one twhree four'], getline(1, '$'))
3597
3598 call setline(1, ['one two', 'three four'])
3599 exe "norm! $3c\<Space>x"
3600 call assert_equal(['one twxhree four'], getline(1, '$'))
3601
3602 set whichwrap+=l
3603 call setline(1, ['one two', 'three four'])
3604 exe "norm! $3x"
3605 call assert_equal(['one twhree four'], getline(1, '$'))
3606 close!
3607 set whichwrap&
3608endfunc
3609
Bram Moolenaar224a5f12020-04-28 20:29:07 +02003610" Test for 'w' and 'b' commands
3611func Test_normal_word_move()
3612 new
3613 call setline(1, ['foo bar a', '', 'foo bar b'])
3614 " copy a single character word at the end of a line
3615 normal 1G$yw
3616 call assert_equal('a', @")
3617 " copy a single character word at the end of a file
3618 normal G$yw
3619 call assert_equal('b', @")
3620 " check for a word movement handling an empty line properly
3621 normal 1G$vwy
3622 call assert_equal("a\n\n", @")
3623
3624 " copy using 'b' command
3625 %d
3626 " non-empty blank line at the start of file
3627 call setline(1, [' ', 'foo bar'])
3628 normal 2Gyb
3629 call assert_equal(" \n", @")
3630 " try to copy backwards from the start of the file
3631 call setline(1, ['one two', 'foo bar'])
3632 call assert_beeps('normal ggyb')
3633 " 'b' command should stop at an empty line
3634 call setline(1, ['one two', '', 'foo bar'])
3635 normal 3Gyb
3636 call assert_equal("\n", @")
3637 normal 3Gy2b
3638 call assert_equal("two\n", @")
3639 " 'b' command should not stop at a non-empty blank line
3640 call setline(1, ['one two', ' ', 'foo bar'])
3641 normal 3Gyb
3642 call assert_equal("two\n ", @")
3643
3644 close!
3645endfunc
3646
Bram Moolenaarbdd2c292020-06-22 21:34:30 +02003647" Test for 'scrolloff' with a long line that doesn't fit in the screen
3648func Test_normal_scroloff()
3649 10new
3650 80vnew
3651 call setline(1, repeat('a', 1000))
3652 set scrolloff=10
3653 normal gg10gj
3654 call assert_equal(8, winline())
3655 normal 10gj
3656 call assert_equal(10, winline())
3657 normal 10gk
3658 call assert_equal(3, winline())
3659 set scrolloff&
3660 close!
3661endfunc
3662
3663" Test for vertical scrolling with CTRL-F and CTRL-B with a long line
3664func Test_normal_vert_scroll_longline()
3665 10new
3666 80vnew
3667 call setline(1, range(1, 10))
3668 call append(5, repeat('a', 1000))
3669 exe "normal gg\<C-F>"
3670 call assert_equal(6, line('.'))
3671 exe "normal \<C-F>\<C-F>"
3672 call assert_equal(11, line('.'))
3673 call assert_equal(1, winline())
3674 exe "normal \<C-B>"
3675 call assert_equal(10, line('.'))
3676 call assert_equal(3, winline())
3677 exe "normal \<C-B>\<C-B>"
3678 call assert_equal(5, line('.'))
3679 call assert_equal(5, winline())
3680 close!
3681endfunc
3682
Bram Moolenaar8a9bc952020-10-02 18:48:07 +02003683" Test for jumping in a file using %
3684func Test_normal_percent_jump()
3685 new
3686 call setline(1, range(1, 100))
3687
3688 " jumping to a folded line should open the fold
3689 25,75fold
3690 call feedkeys('50%', 'xt')
3691 call assert_equal(50, line('.'))
3692 call assert_equal(-1, foldclosedend(50))
3693 close!
3694endfunc
3695
Bram Moolenaar3e72dca2021-05-29 16:30:12 +02003696" Test for << and >> commands to shift text by 'shiftwidth'
3697func Test_normal_shift_rightleft()
3698 new
3699 call setline(1, ['one', '', "\t", ' two', "\tthree", ' four'])
3700 set shiftwidth=2 tabstop=8
3701 normal gg6>>
3702 call assert_equal([' one', '', "\t ", ' two', "\t three", "\tfour"],
3703 \ getline(1, '$'))
3704 normal ggVG2>>
3705 call assert_equal([' one', '', "\t ", "\ttwo",
3706 \ "\t three", "\t four"], getline(1, '$'))
3707 normal gg6<<
3708 call assert_equal([' one', '', "\t ", ' two', "\t three",
3709 \ "\t four"], getline(1, '$'))
3710 normal ggVG2<<
3711 call assert_equal(['one', '', "\t", ' two', "\tthree", ' four'],
3712 \ getline(1, '$'))
3713 set shiftwidth& tabstop&
3714 bw!
3715endfunc
3716
Yegappan Lakshmanan2ac71842021-05-31 19:23:01 +02003717" Some commands like yy, cc, dd, >>, << and !! accept a count after
3718" typing the first letter of the command.
3719func Test_normal_count_after_operator()
3720 new
3721 setlocal shiftwidth=4 tabstop=8 autoindent
3722 call setline(1, ['one', 'two', 'three', 'four', 'five'])
3723 let @a = ''
3724 normal! j"ay4y
3725 call assert_equal("two\nthree\nfour\nfive\n", @a)
3726 normal! 3G>2>
3727 call assert_equal(['one', 'two', ' three', ' four', 'five'],
3728 \ getline(1, '$'))
3729 exe "normal! 3G0c2cred\nblue"
3730 call assert_equal(['one', 'two', ' red', ' blue', 'five'],
3731 \ getline(1, '$'))
3732 exe "normal! gg<8<"
3733 call assert_equal(['one', 'two', 'red', 'blue', 'five'],
3734 \ getline(1, '$'))
3735 exe "normal! ggd3d"
3736 call assert_equal(['blue', 'five'], getline(1, '$'))
3737 call setline(1, range(1, 4))
3738 call feedkeys("gg!3!\<C-B>\"\<CR>", 'xt')
3739 call assert_equal('".,.+2!', @:)
3740 call feedkeys("gg!1!\<C-B>\"\<CR>", 'xt')
3741 call assert_equal('".!', @:)
3742 call feedkeys("gg!9!\<C-B>\"\<CR>", 'xt')
3743 call assert_equal('".,$!', @:)
3744 bw!
3745endfunc
3746
Christian Brabandtaaec1d42021-11-04 13:28:29 +00003747func Test_normal_gj_on_extra_wide_char()
3748 new | 25vsp
3749 let text='1 foooooooo ar e inszwe1 foooooooo inszwei' .
3750 \ ' i drei vier fünf sechs sieben acht un zehn elf zwöfl' .
3751 \ ' dreizehn v ierzehn fünfzehn'
3752 put =text
3753 call cursor(2,1)
3754 norm! gj
3755 call assert_equal([0,2,25,0], getpos('.'))
3756 bw!
3757endfunc
3758
Bram Moolenaar03725c52021-11-24 12:17:53 +00003759func Test_normal_count_out_of_range()
3760 new
3761 call setline(1, 'text')
3762 normal 44444444444|
3763 call assert_equal(999999999, v:count)
3764 normal 444444444444|
3765 call assert_equal(999999999, v:count)
3766 normal 4444444444444|
3767 call assert_equal(999999999, v:count)
3768 normal 4444444444444444444|
3769 call assert_equal(999999999, v:count)
3770
3771 normal 9y99999999|
3772 call assert_equal(899999991, v:count)
3773 normal 10y99999999|
3774 call assert_equal(999999999, v:count)
3775 normal 44444444444y44444444444|
3776 call assert_equal(999999999, v:count)
3777 bwipe!
3778endfunc
3779
Bram Moolenaarf5f1e102020-03-08 05:13:15 +01003780" vim: shiftwidth=2 sts=2 expandtab