xref: /vim-8.2.3635/src/testdir/test_edit.vim (revision 35a9a00a)
1eb992cb9SBram Moolenaar" Test for edit functions
2215ba3b6SBram Moolenaar
3eb992cb9SBram Moolenaarif exists("+t_kD")
4eb992cb9SBram Moolenaar  let &t_kD="[3;*~"
5eb992cb9SBram Moolenaarendif
6eb992cb9SBram Moolenaar
7215ba3b6SBram Moolenaarsource check.vim
8215ba3b6SBram Moolenaar
9eb992cb9SBram Moolenaar" Needed for testing basic rightleft: Test_edit_rightleft
10eb992cb9SBram Moolenaarsource view_util.vim
11eb992cb9SBram Moolenaar
12eb992cb9SBram Moolenaar" Needs to come first until the bug in getchar() is
13eb992cb9SBram Moolenaar" fixed: https://groups.google.com/d/msg/vim_dev/fXL9yme4H4c/bOR-U6_bAQAJ
141e115360SBram Moolenaarfunc Test_edit_00b()
15eb992cb9SBram Moolenaar  new
16eb992cb9SBram Moolenaar  call setline(1, ['abc '])
17eb992cb9SBram Moolenaar  inoreabbr <buffer> h here some more
18eb992cb9SBram Moolenaar  call cursor(1, 4)
19eb992cb9SBram Moolenaar  " <c-l> expands the abbreviation and ends insertmode
20eb992cb9SBram Moolenaar  call feedkeys(":set im\<cr> h\<c-l>:set noim\<cr>", 'tix')
21eb992cb9SBram Moolenaar  call assert_equal(['abc here some more '], getline(1,'$'))
22eb992cb9SBram Moolenaar  iunabbr <buffer> h
23eb992cb9SBram Moolenaar  bw!
24eb992cb9SBram Moolenaarendfunc
25eb992cb9SBram Moolenaar
261e115360SBram Moolenaarfunc Test_edit_01()
27eb992cb9SBram Moolenaar  " set for Travis CI?
28eb992cb9SBram Moolenaar  "  set nocp noesckeys
29eb992cb9SBram Moolenaar  new
30eb992cb9SBram Moolenaar  " 1) empty buffer
31eb992cb9SBram Moolenaar  call assert_equal([''], getline(1,'$'))
32eb992cb9SBram Moolenaar  " 2) delete in an empty line
33eb992cb9SBram Moolenaar  call feedkeys("i\<del>\<esc>", 'tnix')
34eb992cb9SBram Moolenaar  call assert_equal([''], getline(1,'$'))
35eb992cb9SBram Moolenaar  %d
36eb992cb9SBram Moolenaar  " 3) delete one character
37eb992cb9SBram Moolenaar  call setline(1, 'a')
38eb992cb9SBram Moolenaar  call feedkeys("i\<del>\<esc>", 'tnix')
39eb992cb9SBram Moolenaar  call assert_equal([''], getline(1,'$'))
40eb992cb9SBram Moolenaar  %d
41eb992cb9SBram Moolenaar  " 4) delete a multibyte character
42eb992cb9SBram Moolenaar  call setline(1, "\u0401")
43eb992cb9SBram Moolenaar  call feedkeys("i\<del>\<esc>", 'tnix')
44eb992cb9SBram Moolenaar  call assert_equal([''], getline(1,'$'))
45eb992cb9SBram Moolenaar  %d
46eb992cb9SBram Moolenaar  " 5.1) delete linebreak with 'bs' option containing eol
47eb992cb9SBram Moolenaar  let _bs=&bs
48eb992cb9SBram Moolenaar  set bs=eol
49eb992cb9SBram Moolenaar  call setline(1, ["abc def", "ghi jkl"])
50eb992cb9SBram Moolenaar  call cursor(1, 1)
51eb992cb9SBram Moolenaar  call feedkeys("A\<del>\<esc>", 'tnix')
52eb992cb9SBram Moolenaar  call assert_equal(['abc defghi jkl'], getline(1, 2))
53eb992cb9SBram Moolenaar  %d
54eb992cb9SBram Moolenaar  " 5.2) delete linebreak with backspace option w/out eol
55eb992cb9SBram Moolenaar  set bs=
56eb992cb9SBram Moolenaar  call setline(1, ["abc def", "ghi jkl"])
57eb992cb9SBram Moolenaar  call cursor(1, 1)
58eb992cb9SBram Moolenaar  call feedkeys("A\<del>\<esc>", 'tnix')
59eb992cb9SBram Moolenaar  call assert_equal(["abc def", "ghi jkl"], getline(1, 2))
60eb992cb9SBram Moolenaar  let &bs=_bs
61eb992cb9SBram Moolenaar  bw!
62eb992cb9SBram Moolenaarendfunc
63eb992cb9SBram Moolenaar
641e115360SBram Moolenaarfunc Test_edit_02()
65eb992cb9SBram Moolenaar  " Change cursor position in InsertCharPre command
66eb992cb9SBram Moolenaar  new
67eb992cb9SBram Moolenaar  call setline(1, 'abc')
68eb992cb9SBram Moolenaar  call cursor(1, 1)
69eb992cb9SBram Moolenaar  fu! DoIt(...)
70eb992cb9SBram Moolenaar    call cursor(1, 4)
71eb992cb9SBram Moolenaar    if len(a:000)
72eb992cb9SBram Moolenaar      let v:char=a:1
73eb992cb9SBram Moolenaar    endif
74eb992cb9SBram Moolenaar  endfu
75eb992cb9SBram Moolenaar  au InsertCharPre <buffer> :call DoIt('y')
76eb992cb9SBram Moolenaar  call feedkeys("ix\<esc>", 'tnix')
77eb992cb9SBram Moolenaar  call assert_equal(['abcy'], getline(1, '$'))
78eb992cb9SBram Moolenaar  " Setting <Enter> in InsertCharPre
79eb992cb9SBram Moolenaar  au! InsertCharPre <buffer> :call DoIt("\n")
80eb992cb9SBram Moolenaar  call setline(1, 'abc')
81eb992cb9SBram Moolenaar  call cursor(1, 1)
82eb992cb9SBram Moolenaar  call feedkeys("ix\<esc>", 'tnix')
83eb992cb9SBram Moolenaar  call assert_equal(['abc', ''], getline(1, '$'))
84eb992cb9SBram Moolenaar  %d
85eb992cb9SBram Moolenaar  au! InsertCharPre
86eb992cb9SBram Moolenaar  " Change cursor position in InsertEnter command
87eb992cb9SBram Moolenaar  " 1) when setting v:char, keeps changed cursor position
88eb992cb9SBram Moolenaar  au! InsertEnter <buffer> :call DoIt('y')
89eb992cb9SBram Moolenaar  call setline(1, 'abc')
90eb992cb9SBram Moolenaar  call cursor(1, 1)
91eb992cb9SBram Moolenaar  call feedkeys("ix\<esc>", 'tnix')
92eb992cb9SBram Moolenaar  call assert_equal(['abxc'], getline(1, '$'))
93eb992cb9SBram Moolenaar  " 2) when not setting v:char, restores changed cursor position
94eb992cb9SBram Moolenaar  au! InsertEnter <buffer> :call DoIt()
95eb992cb9SBram Moolenaar  call setline(1, 'abc')
96eb992cb9SBram Moolenaar  call cursor(1, 1)
97eb992cb9SBram Moolenaar  call feedkeys("ix\<esc>", 'tnix')
98eb992cb9SBram Moolenaar  call assert_equal(['xabc'], getline(1, '$'))
99eb992cb9SBram Moolenaar  au! InsertEnter
100eb992cb9SBram Moolenaar  delfu DoIt
101eb992cb9SBram Moolenaar  bw!
102eb992cb9SBram Moolenaarendfunc
103eb992cb9SBram Moolenaar
1041e115360SBram Moolenaarfunc Test_edit_03()
105eb992cb9SBram Moolenaar  " Change cursor after <c-o> command to end of line
106eb992cb9SBram Moolenaar  new
107eb992cb9SBram Moolenaar  call setline(1, 'abc')
108eb992cb9SBram Moolenaar  call cursor(1, 1)
109eb992cb9SBram Moolenaar  call feedkeys("i\<c-o>$y\<esc>", 'tnix')
110eb992cb9SBram Moolenaar  call assert_equal(['abcy'], getline(1, '$'))
111eb992cb9SBram Moolenaar  %d
112eb992cb9SBram Moolenaar  call setline(1, 'abc')
113eb992cb9SBram Moolenaar  call cursor(1, 1)
114eb992cb9SBram Moolenaar  call feedkeys("i\<c-o>80|y\<esc>", 'tnix')
115eb992cb9SBram Moolenaar  call assert_equal(['abcy'], getline(1, '$'))
116eb992cb9SBram Moolenaar  %d
117eb992cb9SBram Moolenaar  call setline(1, 'abc')
118eb992cb9SBram Moolenaar  call feedkeys("Ad\<c-o>:s/$/efg/\<cr>hij", 'tnix')
119eb992cb9SBram Moolenaar  call assert_equal(['hijabcdefg'], getline(1, '$'))
120eb992cb9SBram Moolenaar  bw!
121eb992cb9SBram Moolenaarendfunc
122eb992cb9SBram Moolenaar
1231e115360SBram Moolenaarfunc Test_edit_04()
124eb992cb9SBram Moolenaar  " test for :stopinsert
125eb992cb9SBram Moolenaar  new
126eb992cb9SBram Moolenaar  call setline(1, 'abc')
127eb992cb9SBram Moolenaar  call cursor(1, 1)
128eb992cb9SBram Moolenaar  call feedkeys("i\<c-o>:stopinsert\<cr>$", 'tnix')
129eb992cb9SBram Moolenaar  call feedkeys("aX\<esc>", 'tnix')
130eb992cb9SBram Moolenaar  call assert_equal(['abcX'], getline(1, '$'))
131eb992cb9SBram Moolenaar  %d
132eb992cb9SBram Moolenaar  bw!
133eb992cb9SBram Moolenaarendfunc
134eb992cb9SBram Moolenaar
1351e115360SBram Moolenaarfunc Test_edit_05()
136eb992cb9SBram Moolenaar  " test for folds being opened
137eb992cb9SBram Moolenaar  new
138eb992cb9SBram Moolenaar  call setline(1, ['abcX', 'abcX', 'zzzZ'])
139eb992cb9SBram Moolenaar  call cursor(1, 1)
140eb992cb9SBram Moolenaar  set foldmethod=manual foldopen+=insert
141eb992cb9SBram Moolenaar  " create fold for those two lines
142eb992cb9SBram Moolenaar  norm! Vjzf
143eb992cb9SBram Moolenaar  call feedkeys("$ay\<esc>", 'tnix')
144eb992cb9SBram Moolenaar  call assert_equal(['abcXy', 'abcX', 'zzzZ'], getline(1, '$'))
145eb992cb9SBram Moolenaar  %d
146eb992cb9SBram Moolenaar  call setline(1, ['abcX', 'abcX', 'zzzZ'])
147eb992cb9SBram Moolenaar  call cursor(1, 1)
148eb992cb9SBram Moolenaar  set foldmethod=manual foldopen-=insert
149eb992cb9SBram Moolenaar  " create fold for those two lines
150eb992cb9SBram Moolenaar  norm! Vjzf
151eb992cb9SBram Moolenaar  call feedkeys("$ay\<esc>", 'tnix')
152eb992cb9SBram Moolenaar  call assert_equal(['abcXy', 'abcX', 'zzzZ'], getline(1, '$'))
153eb992cb9SBram Moolenaar  %d
154eb992cb9SBram Moolenaar  bw!
155eb992cb9SBram Moolenaarendfunc
156eb992cb9SBram Moolenaar
1571e115360SBram Moolenaarfunc Test_edit_06()
158eb992cb9SBram Moolenaar  " Test in diff mode
1596d91bcb4SBram Moolenaar  CheckFeature diff
1606d91bcb4SBram Moolenaar  CheckExecutable diff
161eb992cb9SBram Moolenaar  new
162eb992cb9SBram Moolenaar  call setline(1, ['abc', 'xxx', 'yyy'])
163eb992cb9SBram Moolenaar  vnew
164eb992cb9SBram Moolenaar  call setline(1, ['abc', 'zzz', 'xxx', 'yyy'])
165eb992cb9SBram Moolenaar  wincmd p
166eb992cb9SBram Moolenaar  diffthis
167eb992cb9SBram Moolenaar  wincmd p
168eb992cb9SBram Moolenaar  diffthis
169eb992cb9SBram Moolenaar  wincmd p
170eb992cb9SBram Moolenaar  call cursor(2, 1)
171eb992cb9SBram Moolenaar  norm! zt
172eb992cb9SBram Moolenaar  call feedkeys("Ozzz\<esc>", 'tnix')
173eb992cb9SBram Moolenaar  call assert_equal(['abc', 'zzz', 'xxx', 'yyy'], getline(1,'$'))
174eb992cb9SBram Moolenaar  bw!
175eb992cb9SBram Moolenaar  bw!
176eb992cb9SBram Moolenaarendfunc
177eb992cb9SBram Moolenaar
1781e115360SBram Moolenaarfunc Test_edit_07()
179eb992cb9SBram Moolenaar  " 1) Test with completion <c-l> when popupmenu is visible
180eb992cb9SBram Moolenaar  new
181eb992cb9SBram Moolenaar  call setline(1, 'J')
182eb992cb9SBram Moolenaar
183eb992cb9SBram Moolenaar  func! ListMonths()
184eb992cb9SBram Moolenaar    call complete(col('.')-1, ['January', 'February', 'March',
185eb992cb9SBram Moolenaar    \ 'April', 'May', 'June', 'July', 'August', 'September',
186eb992cb9SBram Moolenaar    \ 'October', 'November', 'December'])
187eb992cb9SBram Moolenaar    return ''
188eb992cb9SBram Moolenaar  endfunc
189eb992cb9SBram Moolenaar  inoremap <buffer> <F5> <C-R>=ListMonths()<CR>
190eb992cb9SBram Moolenaar
191eb992cb9SBram Moolenaar  call feedkeys("A\<f5>\<c-p>". repeat("\<down>", 6)."\<c-l>\<down>\<c-l>\<cr>", 'tx')
192eb992cb9SBram Moolenaar  call assert_equal(['July'], getline(1,'$'))
193eb992cb9SBram Moolenaar  " 1) Test completion when InsertCharPre kicks in
194eb992cb9SBram Moolenaar  %d
195eb992cb9SBram Moolenaar  call setline(1, 'J')
196eb992cb9SBram Moolenaar  fu! DoIt()
197eb992cb9SBram Moolenaar    if v:char=='u'
198eb992cb9SBram Moolenaar      let v:char='an'
199eb992cb9SBram Moolenaar    endif
200eb992cb9SBram Moolenaar  endfu
201eb992cb9SBram Moolenaar  au InsertCharPre <buffer> :call DoIt()
202eb992cb9SBram Moolenaar  call feedkeys("A\<f5>\<c-p>u\<cr>\<c-l>\<cr>", 'tx')
2034c313b13SBram Moolenaar  call assert_equal(["Jan\<c-l>",''], 1->getline('$'))
204eb992cb9SBram Moolenaar  %d
205eb992cb9SBram Moolenaar  call setline(1, 'J')
206eb992cb9SBram Moolenaar  call feedkeys("A\<f5>\<c-p>u\<down>\<c-l>\<cr>", 'tx')
2074c313b13SBram Moolenaar  call assert_equal(["January"], 1->getline('$'))
208eb992cb9SBram Moolenaar
209eb992cb9SBram Moolenaar  delfu ListMonths
210eb992cb9SBram Moolenaar  delfu DoIt
211eb992cb9SBram Moolenaar  iunmap <buffer> <f5>
212eb992cb9SBram Moolenaar  bw!
213eb992cb9SBram Moolenaarendfunc
214eb992cb9SBram Moolenaar
2151e115360SBram Moolenaarfunc Test_edit_08()
216eb992cb9SBram Moolenaar  " reset insertmode from i_ctrl-r_=
2172a45d64dSBram Moolenaar  let g:bufnr = bufnr('%')
218eb992cb9SBram Moolenaar  new
219eb992cb9SBram Moolenaar  call setline(1, ['abc'])
220eb992cb9SBram Moolenaar  call cursor(1, 4)
2212a45d64dSBram Moolenaar  call feedkeys(":set im\<cr>ZZZ\<c-r>=setbufvar(g:bufnr,'&im', 0)\<cr>",'tnix')
222eb992cb9SBram Moolenaar  call assert_equal(['abZZZc'], getline(1,'$'))
223eb992cb9SBram Moolenaar  call assert_equal([0, 1, 1, 0], getpos('.'))
224eb992cb9SBram Moolenaar  call assert_false(0, '&im')
225eb992cb9SBram Moolenaar  bw!
2262a45d64dSBram Moolenaar  unlet g:bufnr
227eb992cb9SBram Moolenaarendfunc
228eb992cb9SBram Moolenaar
2291e115360SBram Moolenaarfunc Test_edit_09()
230eb992cb9SBram Moolenaar  " test i_CTRL-\ combinations
231eb992cb9SBram Moolenaar  new
232eb992cb9SBram Moolenaar  call setline(1, ['abc', 'def', 'ghi'])
233eb992cb9SBram Moolenaar  call cursor(1, 1)
234eb992cb9SBram Moolenaar  " 1) CTRL-\ CTLR-N
235eb992cb9SBram Moolenaar  call feedkeys(":set im\<cr>\<c-\>\<c-n>ccABC\<c-l>", 'txin')
236eb992cb9SBram Moolenaar  call assert_equal(['ABC', 'def', 'ghi'], getline(1,'$'))
237eb992cb9SBram Moolenaar  call setline(1, ['ABC', 'def', 'ghi'])
238eb992cb9SBram Moolenaar  " 2) CTRL-\ CTLR-G
239eb992cb9SBram Moolenaar  call feedkeys("j0\<c-\>\<c-g>ZZZ\<cr>\<c-l>", 'txin')
240eb992cb9SBram Moolenaar  call assert_equal(['ABC', 'ZZZ', 'def', 'ghi'], getline(1,'$'))
241eb992cb9SBram Moolenaar  call feedkeys("I\<c-\>\<c-g>YYY\<c-l>", 'txin')
242eb992cb9SBram Moolenaar  call assert_equal(['ABC', 'ZZZ', 'YYYdef', 'ghi'], getline(1,'$'))
243eb992cb9SBram Moolenaar  set noinsertmode
244eb992cb9SBram Moolenaar  " 3) CTRL-\ CTRL-O
245eb992cb9SBram Moolenaar  call setline(1, ['ABC', 'ZZZ', 'def', 'ghi'])
246eb992cb9SBram Moolenaar  call cursor(1, 1)
247eb992cb9SBram Moolenaar  call feedkeys("A\<c-o>ix", 'txin')
248eb992cb9SBram Moolenaar  call assert_equal(['ABxC', 'ZZZ', 'def', 'ghi'], getline(1,'$'))
249eb992cb9SBram Moolenaar  call feedkeys("A\<c-\>\<c-o>ix", 'txin')
250eb992cb9SBram Moolenaar  call assert_equal(['ABxCx', 'ZZZ', 'def', 'ghi'], getline(1,'$'))
251eb992cb9SBram Moolenaar  " 4) CTRL-\ a (should be inserted literally, not special after <c-\>
252eb992cb9SBram Moolenaar  call setline(1, ['ABC', 'ZZZ', 'def', 'ghi'])
253eb992cb9SBram Moolenaar  call cursor(1, 1)
254eb992cb9SBram Moolenaar  call feedkeys("A\<c-\>a", 'txin')
255eb992cb9SBram Moolenaar  call assert_equal(["ABC\<c-\>a", 'ZZZ', 'def', 'ghi'], getline(1, '$'))
256eb992cb9SBram Moolenaar  bw!
257eb992cb9SBram Moolenaarendfunc
258eb992cb9SBram Moolenaar
2591e115360SBram Moolenaarfunc Test_edit_11()
260eb992cb9SBram Moolenaar  " Test that indenting kicks in
261eb992cb9SBram Moolenaar  new
262eb992cb9SBram Moolenaar  set cindent
263eb992cb9SBram Moolenaar  call setline(1, ['{', '', ''])
264eb992cb9SBram Moolenaar  call cursor(2, 1)
265eb992cb9SBram Moolenaar  call feedkeys("i\<c-f>int c;\<esc>", 'tnix')
266eb992cb9SBram Moolenaar  call cursor(3, 1)
2671671f448SBram Moolenaar  call feedkeys("\<Insert>/* comment */", 'tnix')
268eb992cb9SBram Moolenaar  call assert_equal(['{', "\<tab>int c;", "/* comment */"], getline(1, '$'))
269eb992cb9SBram Moolenaar  " added changed cindentkeys slightly
270eb992cb9SBram Moolenaar  set cindent cinkeys+=*/
271eb992cb9SBram Moolenaar  call setline(1, ['{', '', ''])
272eb992cb9SBram Moolenaar  call cursor(2, 1)
273eb992cb9SBram Moolenaar  call feedkeys("i\<c-f>int c;\<esc>", 'tnix')
274eb992cb9SBram Moolenaar  call cursor(3, 1)
275eb992cb9SBram Moolenaar  call feedkeys("i/* comment */", 'tnix')
276eb992cb9SBram Moolenaar  call assert_equal(['{', "\<tab>int c;", "\<tab>/* comment */"], getline(1, '$'))
277eb992cb9SBram Moolenaar  set cindent cinkeys+==end
278eb992cb9SBram Moolenaar  call feedkeys("oend\<cr>\<esc>", 'tnix')
279eb992cb9SBram Moolenaar  call assert_equal(['{', "\<tab>int c;", "\<tab>/* comment */", "\tend", ''], getline(1, '$'))
280eb992cb9SBram Moolenaar  set cinkeys-==end
281eb992cb9SBram Moolenaar  %d
282eb992cb9SBram Moolenaar  " Use indentexpr instead of cindenting
283eb992cb9SBram Moolenaar  func! Do_Indent()
284eb992cb9SBram Moolenaar    if v:lnum == 3
285eb992cb9SBram Moolenaar      return 3*shiftwidth()
286eb992cb9SBram Moolenaar    else
287eb992cb9SBram Moolenaar      return 2*shiftwidth()
288eb992cb9SBram Moolenaar    endif
289eb992cb9SBram Moolenaar  endfunc
290eb992cb9SBram Moolenaar  setl indentexpr=Do_Indent() indentkeys+=*/
291eb992cb9SBram Moolenaar  call setline(1, ['{', '', ''])
292eb992cb9SBram Moolenaar  call cursor(2, 1)
293eb992cb9SBram Moolenaar  call feedkeys("i\<c-f>int c;\<esc>", 'tnix')
294eb992cb9SBram Moolenaar  call cursor(3, 1)
295eb992cb9SBram Moolenaar  call feedkeys("i/* comment */", 'tnix')
296eb992cb9SBram Moolenaar  call assert_equal(['{', "\<tab>\<tab>int c;", "\<tab>\<tab>\<tab>/* comment */"], getline(1, '$'))
297eb992cb9SBram Moolenaar  set cinkeys&vim indentkeys&vim
298eb992cb9SBram Moolenaar  set nocindent indentexpr=
299eb992cb9SBram Moolenaar  delfu Do_Indent
300eb992cb9SBram Moolenaar  bw!
301eb992cb9SBram Moolenaarendfunc
302eb992cb9SBram Moolenaar
3031e115360SBram Moolenaarfunc Test_edit_11_indentexpr()
3041b38344eSBram Moolenaar  " Test that indenting kicks in
3051b38344eSBram Moolenaar  new
3061b38344eSBram Moolenaar  " Use indentexpr instead of cindenting
3071b38344eSBram Moolenaar  func! Do_Indent()
3081b38344eSBram Moolenaar    let pline=prevnonblank(v:lnum)
3091b38344eSBram Moolenaar    if empty(getline(v:lnum))
3101b38344eSBram Moolenaar      if getline(pline) =~ 'if\|then'
3111b38344eSBram Moolenaar        return shiftwidth()
3121b38344eSBram Moolenaar      else
3131b38344eSBram Moolenaar        return 0
3141b38344eSBram Moolenaar      endif
3151b38344eSBram Moolenaar    else
3161b38344eSBram Moolenaar        return 0
3171b38344eSBram Moolenaar    endif
3181b38344eSBram Moolenaar  endfunc
3191b38344eSBram Moolenaar  setl indentexpr=Do_Indent() indentkeys+=0=then,0=fi
3201b38344eSBram Moolenaar  call setline(1, ['if [ $this ]'])
3211b38344eSBram Moolenaar  call cursor(1, 1)
3221b38344eSBram Moolenaar  call feedkeys("othen\<cr>that\<cr>fi", 'tnix')
3231b38344eSBram Moolenaar  call assert_equal(['if [ $this ]', "then", "\<tab>that", "fi"], getline(1, '$'))
3241b38344eSBram Moolenaar  set cinkeys&vim indentkeys&vim
3251b38344eSBram Moolenaar  set nocindent indentexpr=
3261b38344eSBram Moolenaar  delfu Do_Indent
3271b38344eSBram Moolenaar  bw!
3281b38344eSBram Moolenaarendfunc
3291b38344eSBram Moolenaar
330eb992cb9SBram Moolenaar" Test changing indent in replace mode
331f9ab52e1SBram Moolenaarfunc Test_edit_12()
332eb992cb9SBram Moolenaar  new
333eb992cb9SBram Moolenaar  call setline(1, ["\tabc", "\tdef"])
334eb992cb9SBram Moolenaar  call cursor(2, 4)
335eb992cb9SBram Moolenaar  call feedkeys("R^\<c-d>", 'tnix')
336eb992cb9SBram Moolenaar  call assert_equal(["\tabc", "def"], getline(1, '$'))
3374c313b13SBram Moolenaar  call assert_equal([0, 2, 2, 0], '.'->getpos())
338eb992cb9SBram Moolenaar  %d
339eb992cb9SBram Moolenaar  call setline(1, ["\tabc", "\t\tdef"])
340eb992cb9SBram Moolenaar  call cursor(2, 2)
341eb992cb9SBram Moolenaar  call feedkeys("R^\<c-d>", 'tnix')
342eb992cb9SBram Moolenaar  call assert_equal(["\tabc", "def"], getline(1, '$'))
343eb992cb9SBram Moolenaar  call assert_equal([0, 2, 1, 0], getpos('.'))
344eb992cb9SBram Moolenaar  %d
345eb992cb9SBram Moolenaar  call setline(1, ["\tabc", "\t\tdef"])
346eb992cb9SBram Moolenaar  call cursor(2, 2)
347eb992cb9SBram Moolenaar  call feedkeys("R\<c-t>", 'tnix')
348eb992cb9SBram Moolenaar  call assert_equal(["\tabc", "\t\t\tdef"], getline(1, '$'))
349eb992cb9SBram Moolenaar  call assert_equal([0, 2, 2, 0], getpos('.'))
350eb992cb9SBram Moolenaar  bw!
351eb992cb9SBram Moolenaar  10vnew
352eb992cb9SBram Moolenaar  call setline(1, ["\tabc", "\t\tdef"])
353eb992cb9SBram Moolenaar  call cursor(2, 2)
354eb992cb9SBram Moolenaar  call feedkeys("R\<c-t>", 'tnix')
355eb992cb9SBram Moolenaar  call assert_equal(["\tabc", "\t\t\tdef"], getline(1, '$'))
356eb992cb9SBram Moolenaar  call assert_equal([0, 2, 2, 0], getpos('.'))
357eb992cb9SBram Moolenaar  %d
358eb992cb9SBram Moolenaar  set sw=4
359eb992cb9SBram Moolenaar  call setline(1, ["\tabc", "\t\tdef"])
360eb992cb9SBram Moolenaar  call cursor(2, 2)
361eb992cb9SBram Moolenaar  call feedkeys("R\<c-t>\<c-t>", 'tnix')
362eb992cb9SBram Moolenaar  call assert_equal(["\tabc", "\t\t\tdef"], getline(1, '$'))
363eb992cb9SBram Moolenaar  call assert_equal([0, 2, 2, 0], getpos('.'))
364eb992cb9SBram Moolenaar  %d
365eb992cb9SBram Moolenaar  call setline(1, ["\tabc", "\t\tdef"])
366eb992cb9SBram Moolenaar  call cursor(2, 2)
367eb992cb9SBram Moolenaar  call feedkeys("R\<c-t>\<c-t>", 'tnix')
368eb992cb9SBram Moolenaar  call assert_equal(["\tabc", "\t\t\tdef"], getline(1, '$'))
369eb992cb9SBram Moolenaar  call assert_equal([0, 2, 2, 0], getpos('.'))
370f9ab52e1SBram Moolenaar  set sw&
371f9ab52e1SBram Moolenaar
372f9ab52e1SBram Moolenaar  " In replace mode, after hitting enter in a line with tab characters,
373f9ab52e1SBram Moolenaar  " pressing backspace should restore the tab characters.
374eb992cb9SBram Moolenaar  %d
375f9ab52e1SBram Moolenaar  setlocal autoindent backspace=2
376f9ab52e1SBram Moolenaar  call setline(1, "\tone\t\ttwo")
377f9ab52e1SBram Moolenaar  exe "normal ggRred\<CR>six" .. repeat("\<BS>", 8)
378f9ab52e1SBram Moolenaar  call assert_equal(["\tone\t\ttwo"], getline(1, '$'))
379eb992cb9SBram Moolenaar  bw!
380eb992cb9SBram Moolenaarendfunc
381eb992cb9SBram Moolenaar
3821e115360SBram Moolenaarfunc Test_edit_13()
383eb992cb9SBram Moolenaar  " Test smartindenting
384eb992cb9SBram Moolenaar  if exists("+smartindent")
385eb992cb9SBram Moolenaar    new
386eb992cb9SBram Moolenaar    set smartindent autoindent
387eb992cb9SBram Moolenaar    call setline(1, ["\tabc"])
388eb992cb9SBram Moolenaar    call feedkeys("A {\<cr>more\<cr>}\<esc>", 'tnix')
389eb992cb9SBram Moolenaar    call assert_equal(["\tabc {", "\t\tmore", "\t}"], getline(1, '$'))
390eb992cb9SBram Moolenaar    set smartindent& autoindent&
3912ba42388SBram Moolenaar    bwipe!
392eb992cb9SBram Moolenaar  endif
3932ba42388SBram Moolenaar
3942ba42388SBram Moolenaar  " Test autoindent removing indent of blank line.
3952ba42388SBram Moolenaar  new
3962ba42388SBram Moolenaar  call setline(1, '    foo bar baz')
3972ba42388SBram Moolenaar  set autoindent
3982ba42388SBram Moolenaar  exe "normal 0eea\<CR>\<CR>\<Esc>"
3992ba42388SBram Moolenaar  call assert_equal("    foo bar", getline(1))
4002ba42388SBram Moolenaar  call assert_equal("", getline(2))
4012ba42388SBram Moolenaar  call assert_equal("    baz", getline(3))
4022ba42388SBram Moolenaar  set autoindent&
403845e0ee5SBram Moolenaar
404845e0ee5SBram Moolenaar  " pressing <C-U> to erase line should keep the indent with 'autoindent'
405845e0ee5SBram Moolenaar  set backspace=2 autoindent
406845e0ee5SBram Moolenaar  %d
407845e0ee5SBram Moolenaar  exe "normal i\tone\<CR>three\<C-U>two"
408845e0ee5SBram Moolenaar  call assert_equal(["\tone", "\ttwo"], getline(1, '$'))
409845e0ee5SBram Moolenaar  set backspace& autoindent&
410845e0ee5SBram Moolenaar
4112ba42388SBram Moolenaar  bwipe!
412eb992cb9SBram Moolenaarendfunc
413eb992cb9SBram Moolenaar
4141f448d90SBram Moolenaar" Test for autoindent removing indent when insert mode is stopped.  Some parts
4151f448d90SBram Moolenaar" of the code is exercised only when interactive mode is used. So use Vim in a
4161f448d90SBram Moolenaar" terminal.
4171f448d90SBram Moolenaarfunc Test_autoindent_remove_indent()
4181f448d90SBram Moolenaar  CheckRunVimInTerminal
4191f448d90SBram Moolenaar  let buf = RunVimInTerminal('-N Xfile', {'rows': 6, 'cols' : 20})
4201f448d90SBram Moolenaar  call TermWait(buf)
4211f448d90SBram Moolenaar  call term_sendkeys(buf, ":set autoindent\n")
4221f448d90SBram Moolenaar  " leaving insert mode in a new line with indent added by autoindent, should
4231f448d90SBram Moolenaar  " remove the indent.
4241f448d90SBram Moolenaar  call term_sendkeys(buf, "i\<Tab>foo\<CR>\<Esc>")
4251f448d90SBram Moolenaar  " Need to delay for sometime, otherwise the code in getchar.c will not be
4261f448d90SBram Moolenaar  " exercised.
4271f448d90SBram Moolenaar  call TermWait(buf, 50)
4281f448d90SBram Moolenaar  " when a line is wrapped and the cursor is at the start of the second line,
4291f448d90SBram Moolenaar  " leaving insert mode, should move the cursor back to the first line.
4301f448d90SBram Moolenaar  call term_sendkeys(buf, "o" .. repeat('x', 20) .. "\<Esc>")
4311f448d90SBram Moolenaar  " Need to delay for sometime, otherwise the code in getchar.c will not be
4321f448d90SBram Moolenaar  " exercised.
4331f448d90SBram Moolenaar  call TermWait(buf, 50)
4341f448d90SBram Moolenaar  call term_sendkeys(buf, ":w\n")
4351f448d90SBram Moolenaar  call TermWait(buf)
4361f448d90SBram Moolenaar  call StopVimInTerminal(buf)
4371f448d90SBram Moolenaar  call assert_equal(["\tfoo", '', repeat('x', 20)], readfile('Xfile'))
4381f448d90SBram Moolenaar  call delete('Xfile')
4391f448d90SBram Moolenaarendfunc
4401f448d90SBram Moolenaar
4411e115360SBram Moolenaarfunc Test_edit_CR()
442eb992cb9SBram Moolenaar  " Test for <CR> in insert mode
443eb992cb9SBram Moolenaar  " basically only in quickfix mode ist tested, the rest
444eb992cb9SBram Moolenaar  " has been taken care of by other tests
4456d91bcb4SBram Moolenaar  CheckFeature quickfix
446eb992cb9SBram Moolenaar  botright new
447eb992cb9SBram Moolenaar  call writefile(range(1, 10), 'Xqflist.txt')
448eb992cb9SBram Moolenaar  call setqflist([{'filename': 'Xqflist.txt', 'lnum': 2}])
449eb992cb9SBram Moolenaar  copen
450eb992cb9SBram Moolenaar  set modifiable
451eb992cb9SBram Moolenaar  call feedkeys("A\<cr>", 'tnix')
452eb992cb9SBram Moolenaar  call assert_equal('Xqflist.txt', bufname(''))
453eb992cb9SBram Moolenaar  call assert_equal(2, line('.'))
454eb992cb9SBram Moolenaar  cclose
455eb992cb9SBram Moolenaar  botright new
456eb992cb9SBram Moolenaar  call setloclist(0, [{'filename': 'Xqflist.txt', 'lnum': 10}])
457eb992cb9SBram Moolenaar  lopen
458eb992cb9SBram Moolenaar  set modifiable
459eb992cb9SBram Moolenaar  call feedkeys("A\<cr>", 'tnix')
460eb992cb9SBram Moolenaar  call assert_equal('Xqflist.txt', bufname(''))
461eb992cb9SBram Moolenaar  call assert_equal(10, line('.'))
462eb992cb9SBram Moolenaar  call feedkeys("A\<Enter>", 'tnix')
463eb992cb9SBram Moolenaar  call feedkeys("A\<kEnter>", 'tnix')
464eb992cb9SBram Moolenaar  call feedkeys("A\n", 'tnix')
465eb992cb9SBram Moolenaar  call feedkeys("A\r", 'tnix')
466eb992cb9SBram Moolenaar  call assert_equal(map(range(1, 10), 'string(v:val)') + ['', '', '', ''], getline(1, '$'))
467eb992cb9SBram Moolenaar  bw!
468eb992cb9SBram Moolenaar  lclose
469eb992cb9SBram Moolenaar  call delete('Xqflist.txt')
470eb992cb9SBram Moolenaarendfunc
471eb992cb9SBram Moolenaar
4721e115360SBram Moolenaarfunc Test_edit_CTRL_()
4736d91bcb4SBram Moolenaar  CheckFeature rightleft
474eb992cb9SBram Moolenaar  " disabled for Windows builds, why?
4756d91bcb4SBram Moolenaar  CheckNotMSWindows
476eb992cb9SBram Moolenaar  let _encoding=&encoding
477eb992cb9SBram Moolenaar  set encoding=utf-8
478eb992cb9SBram Moolenaar  " Test for CTRL-_
479eb992cb9SBram Moolenaar  new
480eb992cb9SBram Moolenaar  call setline(1, ['abc'])
481eb992cb9SBram Moolenaar  call cursor(1, 1)
482eb992cb9SBram Moolenaar  call feedkeys("i\<c-_>xyz\<esc>", 'tnix')
483eb992cb9SBram Moolenaar  call assert_equal(["\<C-_>xyzabc"], getline(1, '$'))
484eb992cb9SBram Moolenaar  call assert_false(&revins)
485eb992cb9SBram Moolenaar  set ari
486eb992cb9SBram Moolenaar  call setline(1, ['abc'])
487eb992cb9SBram Moolenaar  call cursor(1, 1)
488eb992cb9SBram Moolenaar  call feedkeys("i\<c-_>xyz\<esc>", 'tnix')
489eb992cb9SBram Moolenaar  call assert_equal(["æèñabc"], getline(1, '$'))
490eb992cb9SBram Moolenaar  call assert_true(&revins)
491eb992cb9SBram Moolenaar  call setline(1, ['abc'])
492eb992cb9SBram Moolenaar  call cursor(1, 1)
493eb992cb9SBram Moolenaar  call feedkeys("i\<c-_>xyz\<esc>", 'tnix')
494eb992cb9SBram Moolenaar  call assert_equal(["xyzabc"], getline(1, '$'))
495eb992cb9SBram Moolenaar  call assert_false(&revins)
496eb992cb9SBram Moolenaar  set noari
497eb992cb9SBram Moolenaar  let &encoding=_encoding
498eb992cb9SBram Moolenaar  bw!
499eb992cb9SBram Moolenaarendfunc
500eb992cb9SBram Moolenaar
501eb992cb9SBram Moolenaar" needs to come first, to have the @. register empty
5021e115360SBram Moolenaarfunc Test_edit_00a_CTRL_A()
503eb992cb9SBram Moolenaar  " Test pressing CTRL-A
504eb992cb9SBram Moolenaar  new
505eb992cb9SBram Moolenaar  call setline(1, repeat([''], 5))
506eb992cb9SBram Moolenaar  call cursor(1, 1)
507eb992cb9SBram Moolenaar  try
508eb992cb9SBram Moolenaar    call feedkeys("A\<NUL>", 'tnix')
509eb992cb9SBram Moolenaar  catch /^Vim\%((\a\+)\)\=:E29/
510eb992cb9SBram Moolenaar    call assert_true(1, 'E29 error caught')
511eb992cb9SBram Moolenaar  endtry
512eb992cb9SBram Moolenaar  call cursor(1, 1)
513eb992cb9SBram Moolenaar  call feedkeys("Afoobar \<esc>", 'tnix')
514eb992cb9SBram Moolenaar  call cursor(2, 1)
515eb992cb9SBram Moolenaar  call feedkeys("A\<c-a>more\<esc>", 'tnix')
516eb992cb9SBram Moolenaar  call cursor(3, 1)
517eb992cb9SBram Moolenaar  call feedkeys("A\<NUL>and more\<esc>", 'tnix')
518eb992cb9SBram Moolenaar  call assert_equal(['foobar ', 'foobar more', 'foobar morend more', '', ''], getline(1, '$'))
519eb992cb9SBram Moolenaar  bw!
520eb992cb9SBram Moolenaarendfunc
521eb992cb9SBram Moolenaar
5221e115360SBram Moolenaarfunc Test_edit_CTRL_EY()
523eb992cb9SBram Moolenaar  " Ctrl-E/ Ctrl-Y in insert mode completion to scroll
524eb992cb9SBram Moolenaar  10new
525eb992cb9SBram Moolenaar  call setline(1, range(1, 100))
526eb992cb9SBram Moolenaar  call cursor(30, 1)
527eb992cb9SBram Moolenaar  norm! z.
528eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-e>\<c-e>\<c-e>\<c-e>\<c-e>", 'tnix')
529eb992cb9SBram Moolenaar  call assert_equal(30, winsaveview()['topline'])
530eb992cb9SBram Moolenaar  call assert_equal([0, 30, 2, 0], getpos('.'))
531eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-e>\<c-e>\<c-e>\<c-e>\<c-e>", 'tnix')
532eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>".repeat("\<c-y>", 10), 'tnix')
533eb992cb9SBram Moolenaar  call assert_equal(21, winsaveview()['topline'])
534eb992cb9SBram Moolenaar  call assert_equal([0, 30, 2, 0], getpos('.'))
535eb992cb9SBram Moolenaar  bw!
536eb992cb9SBram Moolenaarendfunc
537eb992cb9SBram Moolenaar
5381e115360SBram Moolenaarfunc Test_edit_CTRL_G()
539eb992cb9SBram Moolenaar  new
540eb992cb9SBram Moolenaar  call setline(1, ['foobar', 'foobar', 'foobar'])
541eb992cb9SBram Moolenaar  call cursor(2, 4)
542eb992cb9SBram Moolenaar  call feedkeys("ioooooooo\<c-g>k\<c-r>.\<esc>", 'tnix')
543eb992cb9SBram Moolenaar  call assert_equal(['foooooooooobar', 'foooooooooobar', 'foobar'], getline(1, '$'))
544eb992cb9SBram Moolenaar  call assert_equal([0, 1, 11, 0], getpos('.'))
545eb992cb9SBram Moolenaar  call feedkeys("i\<c-g>k\<esc>", 'tnix')
546eb992cb9SBram Moolenaar  call assert_equal([0, 1, 10, 0], getpos('.'))
547eb992cb9SBram Moolenaar  call cursor(2, 4)
548eb992cb9SBram Moolenaar  call feedkeys("i\<c-g>jzzzz\<esc>", 'tnix')
549eb992cb9SBram Moolenaar  call assert_equal(['foooooooooobar', 'foooooooooobar', 'foozzzzbar'], getline(1, '$'))
550eb992cb9SBram Moolenaar  call assert_equal([0, 3, 7, 0], getpos('.'))
551eb992cb9SBram Moolenaar  call feedkeys("i\<c-g>j\<esc>", 'tnix')
552eb992cb9SBram Moolenaar  call assert_equal([0, 3, 6, 0], getpos('.'))
553eb992cb9SBram Moolenaar  bw!
554eb992cb9SBram Moolenaarendfunc
555eb992cb9SBram Moolenaar
5561e115360SBram Moolenaarfunc Test_edit_CTRL_I()
557eb992cb9SBram Moolenaar  " Tab in completion mode
558eb992cb9SBram Moolenaar  let path=expand("%:p:h")
559eb992cb9SBram Moolenaar  new
560eb992cb9SBram Moolenaar  call setline(1, [path. "/", ''])
561c5379471SBram Moolenaar  call feedkeys("Arunt\<c-x>\<c-f>\<tab>\<cr>\<esc>", 'tnix')
562c5379471SBram Moolenaar  call assert_match('runtest\.vim', getline(1))
563eb992cb9SBram Moolenaar  %d
564eb992cb9SBram Moolenaar  call writefile(['one', 'two', 'three'], 'Xinclude.txt')
565eb992cb9SBram Moolenaar  let include='#include Xinclude.txt'
566eb992cb9SBram Moolenaar  call setline(1, [include, ''])
567eb992cb9SBram Moolenaar  call cursor(2, 1)
568eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<tab>\<cr>\<esc>", 'tnix')
569eb992cb9SBram Moolenaar  call assert_equal([include, 'one', ''], getline(1, '$'))
570eb992cb9SBram Moolenaar  call feedkeys("2ggC\<c-x>\<tab>\<down>\<cr>\<esc>", 'tnix')
571eb992cb9SBram Moolenaar  call assert_equal([include, 'two', ''], getline(1, '$'))
572eb992cb9SBram Moolenaar  call feedkeys("2ggC\<c-x>\<tab>\<down>\<down>\<cr>\<esc>", 'tnix')
573eb992cb9SBram Moolenaar  call assert_equal([include, 'three', ''], getline(1, '$'))
574eb992cb9SBram Moolenaar  call feedkeys("2ggC\<c-x>\<tab>\<down>\<down>\<down>\<cr>\<esc>", 'tnix')
575eb992cb9SBram Moolenaar  call assert_equal([include, '', ''], getline(1, '$'))
576eb992cb9SBram Moolenaar  call delete("Xinclude.txt")
577eb992cb9SBram Moolenaar  bw!
578eb992cb9SBram Moolenaarendfunc
579eb992cb9SBram Moolenaar
5801e115360SBram Moolenaarfunc Test_edit_CTRL_K()
581eb992cb9SBram Moolenaar  " Test pressing CTRL-K (basically only dictionary completion and digraphs
582eb992cb9SBram Moolenaar  " the rest is already covered
583eb992cb9SBram Moolenaar  call writefile(['A', 'AA', 'AAA', 'AAAA'], 'Xdictionary.txt')
584eb992cb9SBram Moolenaar  set dictionary=Xdictionary.txt
585eb992cb9SBram Moolenaar  new
586eb992cb9SBram Moolenaar  call setline(1, 'A')
587eb992cb9SBram Moolenaar  call cursor(1, 1)
588eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-k>\<cr>\<esc>", 'tnix')
589eb992cb9SBram Moolenaar  call assert_equal(['AA', ''], getline(1, '$'))
590eb992cb9SBram Moolenaar  %d
591eb992cb9SBram Moolenaar  call setline(1, 'A')
592eb992cb9SBram Moolenaar  call cursor(1, 1)
593eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-k>\<down>\<cr>\<esc>", 'tnix')
594eb992cb9SBram Moolenaar  call assert_equal(['AAA'], getline(1, '$'))
595eb992cb9SBram Moolenaar  %d
596eb992cb9SBram Moolenaar  call setline(1, 'A')
597eb992cb9SBram Moolenaar  call cursor(1, 1)
598eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-k>\<down>\<down>\<cr>\<esc>", 'tnix')
599eb992cb9SBram Moolenaar  call assert_equal(['AAAA'], getline(1, '$'))
600eb992cb9SBram Moolenaar  %d
601eb992cb9SBram Moolenaar  call setline(1, 'A')
602eb992cb9SBram Moolenaar  call cursor(1, 1)
603eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-k>\<down>\<down>\<down>\<cr>\<esc>", 'tnix')
604eb992cb9SBram Moolenaar  call assert_equal(['A'], getline(1, '$'))
605eb992cb9SBram Moolenaar  %d
606eb992cb9SBram Moolenaar  call setline(1, 'A')
607eb992cb9SBram Moolenaar  call cursor(1, 1)
608eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-k>\<down>\<down>\<down>\<down>\<cr>\<esc>", 'tnix')
609eb992cb9SBram Moolenaar  call assert_equal(['AA'], getline(1, '$'))
610eb992cb9SBram Moolenaar
6114b96df5aSBram Moolenaar  " press an unexpected key after dictionary completion
612eb992cb9SBram Moolenaar  %d
613eb992cb9SBram Moolenaar  call setline(1, 'A')
614eb992cb9SBram Moolenaar  call cursor(1, 1)
615eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-k>\<c-]>\<cr>\<esc>", 'tnix')
616eb992cb9SBram Moolenaar  call assert_equal(['AA', ''], getline(1, '$'))
617eb992cb9SBram Moolenaar  %d
618eb992cb9SBram Moolenaar  call setline(1, 'A')
619eb992cb9SBram Moolenaar  call cursor(1, 1)
620eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-k>\<c-s>\<cr>\<esc>", 'tnix')
621eb992cb9SBram Moolenaar  call assert_equal(["AA\<c-s>", ''], getline(1, '$'))
622eb992cb9SBram Moolenaar  %d
623eb992cb9SBram Moolenaar  call setline(1, 'A')
624eb992cb9SBram Moolenaar  call cursor(1, 1)
625eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-k>\<c-f>\<cr>\<esc>", 'tnix')
626eb992cb9SBram Moolenaar  call assert_equal(["AA\<c-f>", ''], getline(1, '$'))
627eb992cb9SBram Moolenaar
628eb992cb9SBram Moolenaar  set dictionary=
629eb992cb9SBram Moolenaar  %d
630eb992cb9SBram Moolenaar  call setline(1, 'A')
631eb992cb9SBram Moolenaar  call cursor(1, 1)
632eb992cb9SBram Moolenaar  let v:testing = 1
633eb992cb9SBram Moolenaar  try
634eb992cb9SBram Moolenaar    call feedkeys("A\<c-x>\<c-k>\<esc>", 'tnix')
635eb992cb9SBram Moolenaar  catch
636eb992cb9SBram Moolenaar    " error sleeps 2 seconds, when v:testing is not set
637eb992cb9SBram Moolenaar    let v:testing = 0
638eb992cb9SBram Moolenaar  endtry
639eb992cb9SBram Moolenaar  call delete('Xdictionary.txt')
640eb992cb9SBram Moolenaar
641eb992cb9SBram Moolenaar  call test_override("char_avail", 1)
642eb992cb9SBram Moolenaar  set showcmd
643eb992cb9SBram Moolenaar  %d
644eb992cb9SBram Moolenaar  call feedkeys("A\<c-k>a:\<esc>", 'tnix')
645eb992cb9SBram Moolenaar  call assert_equal(['ä'], getline(1, '$'))
646eb992cb9SBram Moolenaar  call test_override("char_avail", 0)
647eb992cb9SBram Moolenaar  set noshowcmd
64830276f2bSBram Moolenaar
649eb992cb9SBram Moolenaar  bw!
650eb992cb9SBram Moolenaarendfunc
651eb992cb9SBram Moolenaar
6521e115360SBram Moolenaarfunc Test_edit_CTRL_L()
653eb992cb9SBram Moolenaar  " Test Ctrl-X Ctrl-L (line completion)
654eb992cb9SBram Moolenaar  new
655eb992cb9SBram Moolenaar  set complete=.
656eb992cb9SBram Moolenaar  call setline(1, ['one', 'two', 'three', '', '', '', ''])
657eb992cb9SBram Moolenaar  call cursor(4, 1)
658eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-l>\<esc>", 'tnix')
659eb992cb9SBram Moolenaar  call assert_equal(['one', 'two', 'three', 'three', '', '', ''], getline(1, '$'))
660eb992cb9SBram Moolenaar  call feedkeys("cct\<c-x>\<c-l>\<c-n>\<esc>", 'tnix')
661eb992cb9SBram Moolenaar  call assert_equal(['one', 'two', 'three', 't', '', '', ''], getline(1, '$'))
662eb992cb9SBram Moolenaar  call feedkeys("cct\<c-x>\<c-l>\<c-n>\<c-n>\<esc>", 'tnix')
663eb992cb9SBram Moolenaar  call assert_equal(['one', 'two', 'three', 'two', '', '', ''], getline(1, '$'))
66402ae9b4aSBram Moolenaar  call feedkeys("cct\<c-x>\<c-l>\<c-n>\<c-n>\<c-n>\<esc>", 'tnix')
665eb992cb9SBram Moolenaar  call assert_equal(['one', 'two', 'three', 'three', '', '', ''], getline(1, '$'))
66602ae9b4aSBram Moolenaar  call feedkeys("cct\<c-x>\<c-l>\<c-n>\<c-n>\<c-n>\<c-n>\<esc>", 'tnix')
66702ae9b4aSBram Moolenaar  call assert_equal(['one', 'two', 'three', 't', '', '', ''], getline(1, '$'))
668eb992cb9SBram Moolenaar  call feedkeys("cct\<c-x>\<c-l>\<c-p>\<esc>", 'tnix')
669eb992cb9SBram Moolenaar  call assert_equal(['one', 'two', 'three', 'two', '', '', ''], getline(1, '$'))
670eb992cb9SBram Moolenaar  call feedkeys("cct\<c-x>\<c-l>\<c-p>\<c-p>\<esc>", 'tnix')
671eb992cb9SBram Moolenaar  call assert_equal(['one', 'two', 'three', 't', '', '', ''], getline(1, '$'))
672eb992cb9SBram Moolenaar  call feedkeys("cct\<c-x>\<c-l>\<c-p>\<c-p>\<c-p>\<esc>", 'tnix')
673eb992cb9SBram Moolenaar  call assert_equal(['one', 'two', 'three', 'three', '', '', ''], getline(1, '$'))
674eb992cb9SBram Moolenaar  set complete=
675eb992cb9SBram Moolenaar  call cursor(5, 1)
676eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-l>\<c-p>\<c-n>\<esc>", 'tnix')
677eb992cb9SBram Moolenaar  call assert_equal(['one', 'two', 'three', 'three', "\<c-l>\<c-p>\<c-n>", '', ''], getline(1, '$'))
678eb992cb9SBram Moolenaar  set complete&
679eb992cb9SBram Moolenaar  %d
680eb992cb9SBram Moolenaar  if has("conceal") && has("syntax")
681eb992cb9SBram Moolenaar    call setline(1, ['foo', 'bar', 'foobar'])
682eb992cb9SBram Moolenaar    call test_override("char_avail", 1)
683eb992cb9SBram Moolenaar    set conceallevel=2 concealcursor=n
684eb992cb9SBram Moolenaar    syn on
685eb992cb9SBram Moolenaar    syn match ErrorMsg "^bar"
686eb992cb9SBram Moolenaar    call matchadd("Conceal", 'oo', 10, -1, {'conceal': 'X'})
687eb992cb9SBram Moolenaar    func! DoIt()
688eb992cb9SBram Moolenaar      let g:change=1
689eb992cb9SBram Moolenaar    endfunc
690eb992cb9SBram Moolenaar    au! TextChangedI <buffer> :call DoIt()
691eb992cb9SBram Moolenaar
692eb992cb9SBram Moolenaar    call cursor(2, 1)
693eb992cb9SBram Moolenaar    call assert_false(exists("g:change"))
694eb992cb9SBram Moolenaar    call feedkeys("A \<esc>", 'tnix')
695eb992cb9SBram Moolenaar    call assert_equal(['foo', 'bar ', 'foobar'], getline(1, '$'))
696eb992cb9SBram Moolenaar    call assert_equal(1, g:change)
697eb992cb9SBram Moolenaar
698eb992cb9SBram Moolenaar    call test_override("char_avail", 0)
699eb992cb9SBram Moolenaar    call clearmatches()
700eb992cb9SBram Moolenaar    syn off
701eb992cb9SBram Moolenaar    au! TextChangedI
702eb992cb9SBram Moolenaar    delfu DoIt
703eb992cb9SBram Moolenaar    unlet! g:change
704eb992cb9SBram Moolenaar  endif
705eb992cb9SBram Moolenaar  bw!
706eb992cb9SBram Moolenaarendfunc
707eb992cb9SBram Moolenaar
7081e115360SBram Moolenaarfunc Test_edit_CTRL_N()
709eb992cb9SBram Moolenaar  " Check keyword completion
710a1070eaeSBram Moolenaar  for e in ['latin1', 'utf-8']
711a1070eaeSBram Moolenaar    exe 'set encoding=' .. e
712eb992cb9SBram Moolenaar    new
713eb992cb9SBram Moolenaar    set complete=.
714eb992cb9SBram Moolenaar    call setline(1, ['INFER', 'loWER', '', '', ])
715eb992cb9SBram Moolenaar    call cursor(3, 1)
716eb992cb9SBram Moolenaar    call feedkeys("Ai\<c-n>\<cr>\<esc>", "tnix")
717eb992cb9SBram Moolenaar    call feedkeys("ILO\<c-n>\<cr>\<esc>", 'tnix')
718a1070eaeSBram Moolenaar    call assert_equal(['INFER', 'loWER', 'i', 'LO', '', ''], getline(1, '$'), e)
719eb992cb9SBram Moolenaar    %d
720eb992cb9SBram Moolenaar    call setline(1, ['INFER', 'loWER', '', '', ])
721eb992cb9SBram Moolenaar    call cursor(3, 1)
722eb992cb9SBram Moolenaar    set ignorecase infercase
723eb992cb9SBram Moolenaar    call feedkeys("Ii\<c-n>\<cr>\<esc>", "tnix")
724eb992cb9SBram Moolenaar    call feedkeys("ILO\<c-n>\<cr>\<esc>", 'tnix')
725a1070eaeSBram Moolenaar    call assert_equal(['INFER', 'loWER', 'infer', 'LOWER', '', ''], getline(1, '$'), e)
726eb992cb9SBram Moolenaar
727eb992cb9SBram Moolenaar    set noignorecase noinfercase complete&
728eb992cb9SBram Moolenaar    bw!
729a1070eaeSBram Moolenaar  endfor
730eb992cb9SBram Moolenaarendfunc
731eb992cb9SBram Moolenaar
7321e115360SBram Moolenaarfunc Test_edit_CTRL_O()
733eb992cb9SBram Moolenaar  " Check for CTRL-O in insert mode
734eb992cb9SBram Moolenaar  new
735eb992cb9SBram Moolenaar  inoreabbr <buffer> h here some more
736eb992cb9SBram Moolenaar  call setline(1, ['abc', 'def'])
737eb992cb9SBram Moolenaar  call cursor(1, 1)
738eb992cb9SBram Moolenaar  " Ctrl-O after an abbreviation
739eb992cb9SBram Moolenaar  exe "norm A h\<c-o>:set nu\<cr> text"
740eb992cb9SBram Moolenaar  call assert_equal(['abc here some more text', 'def'], getline(1, '$'))
741eb992cb9SBram Moolenaar  call assert_true(&nu)
742eb992cb9SBram Moolenaar  set nonu
743eb992cb9SBram Moolenaar  iunabbr <buffer> h
744eb992cb9SBram Moolenaar  " Ctrl-O at end of line with 've'=onemore
745eb992cb9SBram Moolenaar  call cursor(1, 1)
746eb992cb9SBram Moolenaar  call feedkeys("A\<c-o>:let g:a=getpos('.')\<cr>\<esc>", 'tnix')
747eb992cb9SBram Moolenaar  call assert_equal([0, 1, 23, 0], g:a)
748eb992cb9SBram Moolenaar  call cursor(1, 1)
749eb992cb9SBram Moolenaar  set ve=onemore
750eb992cb9SBram Moolenaar  call feedkeys("A\<c-o>:let g:a=getpos('.')\<cr>\<esc>", 'tnix')
751eb992cb9SBram Moolenaar  call assert_equal([0, 1, 24, 0], g:a)
752eb992cb9SBram Moolenaar  set ve=
753eb992cb9SBram Moolenaar  unlet! g:a
754eb992cb9SBram Moolenaar  bw!
755eb992cb9SBram Moolenaarendfunc
756eb992cb9SBram Moolenaar
7571e115360SBram Moolenaarfunc Test_edit_CTRL_R()
758eb992cb9SBram Moolenaar  " Insert Register
759eb992cb9SBram Moolenaar  new
760eb992cb9SBram Moolenaar  call test_override("ALL", 1)
761eb992cb9SBram Moolenaar  set showcmd
762eb992cb9SBram Moolenaar  call feedkeys("AFOOBAR eins zwei\<esc>", 'tnix')
763eb992cb9SBram Moolenaar  call feedkeys("O\<c-r>.", 'tnix')
764eb992cb9SBram Moolenaar  call feedkeys("O\<c-r>=10*500\<cr>\<esc>", 'tnix')
765eb992cb9SBram Moolenaar  call feedkeys("O\<c-r>=getreg('=', 1)\<cr>\<esc>", 'tnix')
766eb992cb9SBram Moolenaar  call assert_equal(["getreg('=', 1)", '5000', "FOOBAR eins zwei", "FOOBAR eins zwei"], getline(1, '$'))
767eb992cb9SBram Moolenaar  call test_override("ALL", 0)
768eb992cb9SBram Moolenaar  set noshowcmd
769eb992cb9SBram Moolenaar  bw!
770eb992cb9SBram Moolenaarendfunc
771eb992cb9SBram Moolenaar
7721e115360SBram Moolenaarfunc Test_edit_CTRL_S()
773eb992cb9SBram Moolenaar  " Test pressing CTRL-S (basically only spellfile completion)
774eb992cb9SBram Moolenaar  " the rest is already covered
775eb992cb9SBram Moolenaar  new
776eb992cb9SBram Moolenaar  if !has("spell")
777eb992cb9SBram Moolenaar    call setline(1, 'vim')
778eb992cb9SBram Moolenaar    call feedkeys("A\<c-x>ss\<cr>\<esc>", 'tnix')
779eb992cb9SBram Moolenaar    call assert_equal(['vims', ''], getline(1, '$'))
780eb992cb9SBram Moolenaar    bw!
781eb992cb9SBram Moolenaar    return
782eb992cb9SBram Moolenaar  endif
783eb992cb9SBram Moolenaar  call setline(1, 'vim')
784eb992cb9SBram Moolenaar  " spell option not yet set
785eb992cb9SBram Moolenaar  try
786eb992cb9SBram Moolenaar    call feedkeys("A\<c-x>\<c-s>\<cr>\<esc>", 'tnix')
787eb992cb9SBram Moolenaar  catch /^Vim\%((\a\+)\)\=:E756/
788eb992cb9SBram Moolenaar    call assert_true(1, 'error caught')
789eb992cb9SBram Moolenaar  endtry
790eb992cb9SBram Moolenaar  call assert_equal(['vim', ''], getline(1, '$'))
791eb992cb9SBram Moolenaar  %d
792eb992cb9SBram Moolenaar  setl spell spelllang=en
793eb992cb9SBram Moolenaar  call setline(1, 'vim')
794eb992cb9SBram Moolenaar  call cursor(1, 1)
795eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-s>\<cr>\<esc>", 'tnix')
796eb992cb9SBram Moolenaar  call assert_equal(['Vim', ''], getline(1, '$'))
797eb992cb9SBram Moolenaar  %d
798eb992cb9SBram Moolenaar  call setline(1, 'vim')
799eb992cb9SBram Moolenaar  call cursor(1, 1)
800eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-s>\<down>\<cr>\<esc>", 'tnix')
801eb992cb9SBram Moolenaar  call assert_equal(['Aim'], getline(1, '$'))
802eb992cb9SBram Moolenaar  %d
803eb992cb9SBram Moolenaar  call setline(1, 'vim')
804eb992cb9SBram Moolenaar  call cursor(1, 1)
805eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-s>\<c-p>\<cr>\<esc>", 'tnix')
806eb992cb9SBram Moolenaar  call assert_equal(['vim', ''], getline(1, '$'))
807eb992cb9SBram Moolenaar  %d
808eb992cb9SBram Moolenaar  " empty buffer
809eb992cb9SBram Moolenaar  call cursor(1, 1)
810eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-s>\<c-p>\<cr>\<esc>", 'tnix')
811eb992cb9SBram Moolenaar  call assert_equal(['', ''], getline(1, '$'))
812eb992cb9SBram Moolenaar  setl nospell
813eb992cb9SBram Moolenaar  bw!
814eb992cb9SBram Moolenaarendfunc
815eb992cb9SBram Moolenaar
8161e115360SBram Moolenaarfunc Test_edit_CTRL_T()
817eb992cb9SBram Moolenaar  " Check for CTRL-T and CTRL-X CTRL-T in insert mode
818eb992cb9SBram Moolenaar  " 1) increase indent
819eb992cb9SBram Moolenaar  new
820eb992cb9SBram Moolenaar  call setline(1, "abc")
821eb992cb9SBram Moolenaar  call cursor(1, 1)
822eb992cb9SBram Moolenaar  call feedkeys("A\<c-t>xyz", 'tnix')
823eb992cb9SBram Moolenaar  call assert_equal(["\<tab>abcxyz"], getline(1, '$'))
824eb992cb9SBram Moolenaar  " 2) also when paste option is set
825eb992cb9SBram Moolenaar  set paste
826eb992cb9SBram Moolenaar  call setline(1, "abc")
827eb992cb9SBram Moolenaar  call cursor(1, 1)
828eb992cb9SBram Moolenaar  call feedkeys("A\<c-t>xyz", 'tnix')
829eb992cb9SBram Moolenaar  call assert_equal(["\<tab>abcxyz"], getline(1, '$'))
830eb992cb9SBram Moolenaar  set nopaste
831eb992cb9SBram Moolenaar  " CTRL-X CTRL-T (thesaurus complete)
832eb992cb9SBram Moolenaar  call writefile(['angry furious mad enraged'], 'Xthesaurus')
833eb992cb9SBram Moolenaar  set thesaurus=Xthesaurus
834eb992cb9SBram Moolenaar  call setline(1, 'mad')
835eb992cb9SBram Moolenaar  call cursor(1, 1)
836eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-t>\<cr>\<esc>", 'tnix')
837eb992cb9SBram Moolenaar  call assert_equal(['mad', ''], getline(1, '$'))
838eb992cb9SBram Moolenaar  %d
839eb992cb9SBram Moolenaar  call setline(1, 'mad')
840eb992cb9SBram Moolenaar  call cursor(1, 1)
841eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-t>\<c-n>\<cr>\<esc>", 'tnix')
842eb992cb9SBram Moolenaar  call assert_equal(['angry', ''], getline(1, '$'))
843eb992cb9SBram Moolenaar  %d
844eb992cb9SBram Moolenaar  call setline(1, 'mad')
845eb992cb9SBram Moolenaar  call cursor(1, 1)
846eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-t>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
847eb992cb9SBram Moolenaar  call assert_equal(['furious', ''], getline(1, '$'))
848eb992cb9SBram Moolenaar  %d
849eb992cb9SBram Moolenaar  call setline(1, 'mad')
850eb992cb9SBram Moolenaar  call cursor(1, 1)
851eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-t>\<c-n>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
852eb992cb9SBram Moolenaar  call assert_equal(['enraged', ''], getline(1, '$'))
853eb992cb9SBram Moolenaar  %d
854eb992cb9SBram Moolenaar  call setline(1, 'mad')
855eb992cb9SBram Moolenaar  call cursor(1, 1)
856eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-t>\<c-n>\<c-n>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
857eb992cb9SBram Moolenaar  call assert_equal(['mad', ''], getline(1, '$'))
858eb992cb9SBram Moolenaar  %d
859eb992cb9SBram Moolenaar  call setline(1, 'mad')
860eb992cb9SBram Moolenaar  call cursor(1, 1)
861eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-t>\<c-n>\<c-n>\<c-n>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
862eb992cb9SBram Moolenaar  call assert_equal(['mad', ''], getline(1, '$'))
863eb992cb9SBram Moolenaar  " Using <c-p> <c-n> when 'complete' is empty
864eb992cb9SBram Moolenaar  set complete=
865eb992cb9SBram Moolenaar  %d
866eb992cb9SBram Moolenaar  call setline(1, 'mad')
867eb992cb9SBram Moolenaar  call cursor(1, 1)
868eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-t>\<c-n>\<cr>\<esc>", 'tnix')
869eb992cb9SBram Moolenaar  call assert_equal(['angry', ''], getline(1, '$'))
870eb992cb9SBram Moolenaar  %d
871eb992cb9SBram Moolenaar  call setline(1, 'mad')
872eb992cb9SBram Moolenaar  call cursor(1, 1)
873eb992cb9SBram Moolenaar  call feedkeys("A\<c-x>\<c-t>\<c-p>\<cr>\<esc>", 'tnix')
874eb992cb9SBram Moolenaar  call assert_equal(['mad', ''], getline(1, '$'))
875eb992cb9SBram Moolenaar  set complete&
876eb992cb9SBram Moolenaar
877eb992cb9SBram Moolenaar  set thesaurus=
878eb992cb9SBram Moolenaar  %d
879eb992cb9SBram Moolenaar  call setline(1, 'mad')
880eb992cb9SBram Moolenaar  call cursor(1, 1)
881eb992cb9SBram Moolenaar  let v:testing = 1
882eb992cb9SBram Moolenaar  try
883eb992cb9SBram Moolenaar    call feedkeys("A\<c-x>\<c-t>\<esc>", 'tnix')
884eb992cb9SBram Moolenaar  catch
885eb992cb9SBram Moolenaar    " error sleeps 2 seconds, when v:testing is not set
886eb992cb9SBram Moolenaar    let v:testing = 0
887eb992cb9SBram Moolenaar  endtry
888eb992cb9SBram Moolenaar  call assert_equal(['mad'], getline(1, '$'))
889eb992cb9SBram Moolenaar  call delete('Xthesaurus')
890eb992cb9SBram Moolenaar  bw!
891eb992cb9SBram Moolenaarendfunc
892eb992cb9SBram Moolenaar
8931e115360SBram Moolenaarfunc Test_edit_CTRL_U()
894eb992cb9SBram Moolenaar  " Test 'completefunc'
895eb992cb9SBram Moolenaar  new
896eb992cb9SBram Moolenaar  " -1, -2 and -3 are special return values
897eb992cb9SBram Moolenaar  let g:special=0
898eb992cb9SBram Moolenaar  fun! CompleteMonths(findstart, base)
899eb992cb9SBram Moolenaar    if a:findstart
900eb992cb9SBram Moolenaar      " locate the start of the word
901eb992cb9SBram Moolenaar      return g:special
902eb992cb9SBram Moolenaar    else
903eb992cb9SBram Moolenaar      " find months matching with "a:base"
904eb992cb9SBram Moolenaar      let res = []
905eb992cb9SBram Moolenaar      for m in split("Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec")
906eb992cb9SBram Moolenaar        if m =~ '^\c'.a:base
907eb992cb9SBram Moolenaar          call add(res, {'word': m, 'abbr': m.' Month', 'icase': 0})
908eb992cb9SBram Moolenaar        endif
909eb992cb9SBram Moolenaar      endfor
910eb992cb9SBram Moolenaar      return {'words': res, 'refresh': 'always'}
911eb992cb9SBram Moolenaar    endif
912eb992cb9SBram Moolenaar  endfun
913eb992cb9SBram Moolenaar  set completefunc=CompleteMonths
914eb992cb9SBram Moolenaar  call setline(1, ['', ''])
915eb992cb9SBram Moolenaar  call cursor(1, 1)
916eb992cb9SBram Moolenaar  call feedkeys("AX\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
917eb992cb9SBram Moolenaar  call assert_equal(['X', '', ''], getline(1, '$'))
918eb992cb9SBram Moolenaar  %d
919eb992cb9SBram Moolenaar  let g:special=-1
920eb992cb9SBram Moolenaar  call feedkeys("AX\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
921eb992cb9SBram Moolenaar  call assert_equal(['XJan', ''], getline(1, '$'))
922eb992cb9SBram Moolenaar  %d
923eb992cb9SBram Moolenaar  let g:special=-2
924eb992cb9SBram Moolenaar  call feedkeys("AX\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
925eb992cb9SBram Moolenaar  call assert_equal(['X', ''], getline(1, '$'))
926eb992cb9SBram Moolenaar  %d
927eb992cb9SBram Moolenaar  let g:special=-3
928eb992cb9SBram Moolenaar  call feedkeys("AX\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
929eb992cb9SBram Moolenaar  call assert_equal(['X', ''], getline(1, '$'))
930eb992cb9SBram Moolenaar  %d
931eb992cb9SBram Moolenaar  let g:special=0
932eb992cb9SBram Moolenaar  call feedkeys("AM\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
933eb992cb9SBram Moolenaar  call assert_equal(['Mar', ''], getline(1, '$'))
934eb992cb9SBram Moolenaar  %d
935eb992cb9SBram Moolenaar  call feedkeys("AM\<c-x>\<c-u>\<c-n>\<cr>\<esc>", 'tnix')
936eb992cb9SBram Moolenaar  call assert_equal(['May', ''], getline(1, '$'))
937eb992cb9SBram Moolenaar  %d
938eb992cb9SBram Moolenaar  call feedkeys("AM\<c-x>\<c-u>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
939eb992cb9SBram Moolenaar  call assert_equal(['M', ''], getline(1, '$'))
940eb992cb9SBram Moolenaar  delfu CompleteMonths
941eb992cb9SBram Moolenaar  %d
942eb992cb9SBram Moolenaar  try
943eb992cb9SBram Moolenaar    call feedkeys("A\<c-x>\<c-u>", 'tnix')
944eb992cb9SBram Moolenaar    call assert_fails(1, 'unknown completion function')
945eb992cb9SBram Moolenaar  catch /^Vim\%((\a\+)\)\=:E117/
946eb992cb9SBram Moolenaar    call assert_true(1, 'E117 error caught')
947eb992cb9SBram Moolenaar  endtry
948eb992cb9SBram Moolenaar  set completefunc=
949eb992cb9SBram Moolenaar  bw!
950eb992cb9SBram Moolenaarendfunc
951eb992cb9SBram Moolenaar
952ff06f283SBram Moolenaarfunc Test_edit_completefunc_delete()
953ff06f283SBram Moolenaar  func CompleteFunc(findstart, base)
954ff06f283SBram Moolenaar    if a:findstart == 1
955ff06f283SBram Moolenaar      return col('.') - 1
956ff06f283SBram Moolenaar    endif
957ff06f283SBram Moolenaar    normal dd
958ff06f283SBram Moolenaar    return ['a', 'b']
959ff06f283SBram Moolenaar  endfunc
960ff06f283SBram Moolenaar  new
961ff06f283SBram Moolenaar  set completefunc=CompleteFunc
962ff06f283SBram Moolenaar  call setline(1, ['', 'abcd', ''])
963ff06f283SBram Moolenaar  2d
9646adb9ea0SBram Moolenaar  call assert_fails("normal 2G$a\<C-X>\<C-U>", 'E578:')
965ff06f283SBram Moolenaar  bwipe!
966ff06f283SBram Moolenaarendfunc
967ff06f283SBram Moolenaar
968ff06f283SBram Moolenaar
9691e115360SBram Moolenaarfunc Test_edit_CTRL_Z()
970eb992cb9SBram Moolenaar  " Ctrl-Z when insertmode is not set inserts it literally
971eb992cb9SBram Moolenaar  new
972eb992cb9SBram Moolenaar  call setline(1, 'abc')
973eb992cb9SBram Moolenaar  call feedkeys("A\<c-z>\<esc>", 'tnix')
974eb992cb9SBram Moolenaar  call assert_equal(["abc\<c-z>"], getline(1,'$'))
975eb992cb9SBram Moolenaar  bw!
976eb992cb9SBram Moolenaar  " TODO: How to Test Ctrl-Z in insert mode, e.g. suspend?
977eb992cb9SBram Moolenaarendfunc
978eb992cb9SBram Moolenaar
9791e115360SBram Moolenaarfunc Test_edit_DROP()
9806d91bcb4SBram Moolenaar  CheckFeature dnd
981eb992cb9SBram Moolenaar  new
982eb992cb9SBram Moolenaar  call setline(1, ['abc def ghi'])
983eb992cb9SBram Moolenaar  call cursor(1, 1)
984eb992cb9SBram Moolenaar  try
985eb992cb9SBram Moolenaar    call feedkeys("i\<Drop>\<Esc>", 'tnix')
986eb992cb9SBram Moolenaar    call assert_fails(1, 'Invalid register name')
987eb992cb9SBram Moolenaar  catch /^Vim\%((\a\+)\)\=:E353/
988eb992cb9SBram Moolenaar    call assert_true(1, 'error caught')
989eb992cb9SBram Moolenaar  endtry
990eb992cb9SBram Moolenaar  bw!
991eb992cb9SBram Moolenaarendfunc
992eb992cb9SBram Moolenaar
9931e115360SBram Moolenaarfunc Test_edit_CTRL_V()
9946d91bcb4SBram Moolenaar  CheckFeature ebcdic
995eb992cb9SBram Moolenaar  new
996eb992cb9SBram Moolenaar  call setline(1, ['abc'])
997eb992cb9SBram Moolenaar  call cursor(2, 1)
998eb992cb9SBram Moolenaar  " force some redraws
999eb992cb9SBram Moolenaar  set showmode showcmd
1000eb992cb9SBram Moolenaar  "call test_override_char_avail(1)
1001eb992cb9SBram Moolenaar  call test_override('ALL', 1)
1002eb992cb9SBram Moolenaar  call feedkeys("A\<c-v>\<c-n>\<c-v>\<c-l>\<c-v>\<c-b>\<esc>", 'tnix')
1003eb992cb9SBram Moolenaar  call assert_equal(["abc\x0e\x0c\x02"], getline(1, '$'))
1004eb992cb9SBram Moolenaar
1005eb992cb9SBram Moolenaar  if has("rightleft") && exists("+rl")
1006eb992cb9SBram Moolenaar    set rl
1007eb992cb9SBram Moolenaar    call setline(1, ['abc'])
1008eb992cb9SBram Moolenaar    call cursor(2, 1)
1009eb992cb9SBram Moolenaar    call feedkeys("A\<c-v>\<c-n>\<c-v>\<c-l>\<c-v>\<c-b>\<esc>", 'tnix')
1010eb992cb9SBram Moolenaar    call assert_equal(["abc\x0e\x0c\x02"], getline(1, '$'))
1011eb992cb9SBram Moolenaar    set norl
1012eb992cb9SBram Moolenaar  endif
1013eb992cb9SBram Moolenaar
1014eb992cb9SBram Moolenaar  call test_override('ALL', 0)
1015eb992cb9SBram Moolenaar  set noshowmode showcmd
1016eb992cb9SBram Moolenaar  bw!
1017eb992cb9SBram Moolenaarendfunc
1018eb992cb9SBram Moolenaar
10191e115360SBram Moolenaarfunc Test_edit_F1()
10205a4c3082SBram Moolenaar  CheckFeature quickfix
10215a4c3082SBram Moolenaar
1022eb992cb9SBram Moolenaar  " Pressing <f1>
1023eb992cb9SBram Moolenaar  new
1024eb992cb9SBram Moolenaar  call feedkeys(":set im\<cr>\<f1>\<c-l>", 'tnix')
1025eb992cb9SBram Moolenaar  set noinsertmode
1026eb992cb9SBram Moolenaar  call assert_equal('help', &buftype)
1027eb992cb9SBram Moolenaar  bw
1028eb992cb9SBram Moolenaar  bw
1029eb992cb9SBram Moolenaarendfunc
1030eb992cb9SBram Moolenaar
10311e115360SBram Moolenaarfunc Test_edit_F21()
1032eb992cb9SBram Moolenaar  " Pressing <f21>
1033eb992cb9SBram Moolenaar  " sends a netbeans command
10346d91bcb4SBram Moolenaar  CheckFeature netbeans_intg
1035eb992cb9SBram Moolenaar  new
1036eb992cb9SBram Moolenaar  " I have no idea what this is supposed to do :)
1037eb992cb9SBram Moolenaar  call feedkeys("A\<F21>\<F1>\<esc>", 'tnix')
1038eb992cb9SBram Moolenaar  bw
1039eb992cb9SBram Moolenaarendfunc
1040eb992cb9SBram Moolenaar
10411e115360SBram Moolenaarfunc Test_edit_HOME_END()
1042eb992cb9SBram Moolenaar  " Test Home/End Keys
1043eb992cb9SBram Moolenaar  new
1044eb992cb9SBram Moolenaar  set foldopen+=hor
1045eb992cb9SBram Moolenaar  call setline(1, ['abc', 'def'])
1046eb992cb9SBram Moolenaar  call cursor(1, 1)
1047eb992cb9SBram Moolenaar  call feedkeys("AX\<Home>Y\<esc>", 'tnix')
1048eb992cb9SBram Moolenaar  call cursor(2, 1)
1049eb992cb9SBram Moolenaar  call feedkeys("iZ\<End>Y\<esc>", 'tnix')
1050eb992cb9SBram Moolenaar  call assert_equal(['YabcX', 'ZdefY'], getline(1, '$'))
1051eb992cb9SBram Moolenaar
1052eb992cb9SBram Moolenaar  set foldopen-=hor
1053eb992cb9SBram Moolenaar  bw!
1054eb992cb9SBram Moolenaarendfunc
1055eb992cb9SBram Moolenaar
10561e115360SBram Moolenaarfunc Test_edit_INS()
1057eb992cb9SBram Moolenaar  " Test for Pressing <Insert>
1058eb992cb9SBram Moolenaar  new
1059eb992cb9SBram Moolenaar  call setline(1, ['abc', 'def'])
1060eb992cb9SBram Moolenaar  call cursor(1, 1)
1061eb992cb9SBram Moolenaar  call feedkeys("i\<Insert>ZYX>", 'tnix')
1062eb992cb9SBram Moolenaar  call assert_equal(['ZYX>', 'def'], getline(1, '$'))
1063eb992cb9SBram Moolenaar  call setline(1, ['abc', 'def'])
1064eb992cb9SBram Moolenaar  call cursor(1, 1)
1065eb992cb9SBram Moolenaar  call feedkeys("i\<Insert>Z\<Insert>YX>", 'tnix')
1066eb992cb9SBram Moolenaar  call assert_equal(['ZYX>bc', 'def'], getline(1, '$'))
1067eb992cb9SBram Moolenaar  bw!
1068eb992cb9SBram Moolenaarendfunc
1069eb992cb9SBram Moolenaar
10701e115360SBram Moolenaarfunc Test_edit_LEFT_RIGHT()
1071eb992cb9SBram Moolenaar  " Left, Shift-Left, Right, Shift-Right
1072eb992cb9SBram Moolenaar  new
1073eb992cb9SBram Moolenaar  call setline(1, ['abc def ghi', 'ABC DEF GHI', 'ZZZ YYY XXX'])
1074eb992cb9SBram Moolenaar  let _ww=&ww
1075eb992cb9SBram Moolenaar  set ww=
1076eb992cb9SBram Moolenaar  call cursor(2, 1)
1077eb992cb9SBram Moolenaar  call feedkeys("i\<left>\<esc>", 'tnix')
1078eb992cb9SBram Moolenaar  call assert_equal([0, 2, 1, 0], getpos('.'))
1079eb992cb9SBram Moolenaar  " Is this a bug, <s-left> does not respect whichwrap option
1080eb992cb9SBram Moolenaar  call feedkeys("i\<s-left>\<esc>", 'tnix')
1081eb992cb9SBram Moolenaar  call assert_equal([0, 1, 8, 0], getpos('.'))
1082eb992cb9SBram Moolenaar  call feedkeys("i". repeat("\<s-left>", 3). "\<esc>", 'tnix')
1083eb992cb9SBram Moolenaar  call assert_equal([0, 1, 1, 0], getpos('.'))
1084eb992cb9SBram Moolenaar  call feedkeys("i\<right>\<esc>", 'tnix')
1085eb992cb9SBram Moolenaar  call assert_equal([0, 1, 1, 0], getpos('.'))
1086eb992cb9SBram Moolenaar  call feedkeys("i\<right>\<right>\<esc>", 'tnix')
1087eb992cb9SBram Moolenaar  call assert_equal([0, 1, 2, 0], getpos('.'))
1088eb992cb9SBram Moolenaar  call feedkeys("A\<right>\<esc>", 'tnix')
1089eb992cb9SBram Moolenaar  call assert_equal([0, 1, 11, 0], getpos('.'))
1090eb992cb9SBram Moolenaar  call feedkeys("A\<s-right>\<esc>", 'tnix')
1091eb992cb9SBram Moolenaar  call assert_equal([0, 2, 1, 0], getpos('.'))
1092eb992cb9SBram Moolenaar  call feedkeys("i\<s-right>\<esc>", 'tnix')
1093eb992cb9SBram Moolenaar  call assert_equal([0, 2, 4, 0], getpos('.'))
1094eb992cb9SBram Moolenaar  call cursor(3, 11)
1095eb992cb9SBram Moolenaar  call feedkeys("A\<right>\<esc>", 'tnix')
1096eb992cb9SBram Moolenaar  call feedkeys("A\<s-right>\<esc>", 'tnix')
1097eb992cb9SBram Moolenaar  call assert_equal([0, 3, 11, 0], getpos('.'))
1098eb992cb9SBram Moolenaar  call cursor(2, 11)
1099eb992cb9SBram Moolenaar  " <S-Right> does not respect 'whichwrap' option
1100eb992cb9SBram Moolenaar  call feedkeys("A\<s-right>\<esc>", 'tnix')
1101eb992cb9SBram Moolenaar  call assert_equal([0, 3, 1, 0], getpos('.'))
1102eb992cb9SBram Moolenaar  " Check motion when 'whichwrap' contains cursor keys for insert mode
1103eb992cb9SBram Moolenaar  set ww+=[,]
1104eb992cb9SBram Moolenaar  call cursor(2, 1)
1105eb992cb9SBram Moolenaar  call feedkeys("i\<left>\<esc>", 'tnix')
1106eb992cb9SBram Moolenaar  call assert_equal([0, 1, 11, 0], getpos('.'))
1107eb992cb9SBram Moolenaar  call cursor(2, 11)
1108eb992cb9SBram Moolenaar  call feedkeys("A\<right>\<esc>", 'tnix')
1109eb992cb9SBram Moolenaar  call assert_equal([0, 3, 1, 0], getpos('.'))
1110eb992cb9SBram Moolenaar  call cursor(2, 11)
1111eb992cb9SBram Moolenaar  call feedkeys("A\<s-right>\<esc>", 'tnix')
1112eb992cb9SBram Moolenaar  call assert_equal([0, 3, 1, 0], getpos('.'))
1113eb992cb9SBram Moolenaar  let &ww = _ww
1114eb992cb9SBram Moolenaar  bw!
1115eb992cb9SBram Moolenaarendfunc
1116eb992cb9SBram Moolenaar
11171e115360SBram Moolenaarfunc Test_edit_MOUSE()
1118eb992cb9SBram Moolenaar  " This is a simple test, since we not really using the mouse here
11196d91bcb4SBram Moolenaar  CheckFeature mouse
1120eb992cb9SBram Moolenaar  10new
1121eb992cb9SBram Moolenaar  call setline(1, range(1, 100))
1122eb992cb9SBram Moolenaar  call cursor(1, 1)
1123eb992cb9SBram Moolenaar  set mouse=a
1124eb992cb9SBram Moolenaar  call feedkeys("A\<ScrollWheelDown>\<esc>", 'tnix')
1125eb992cb9SBram Moolenaar  call assert_equal([0, 4, 1, 0], getpos('.'))
1126eb992cb9SBram Moolenaar  " This should move by one pageDown, but only moves
1127eb992cb9SBram Moolenaar  " by one line when the test is run...
1128eb992cb9SBram Moolenaar  call feedkeys("A\<S-ScrollWheelDown>\<esc>", 'tnix')
1129eb992cb9SBram Moolenaar  call assert_equal([0, 5, 1, 0], getpos('.'))
1130eb992cb9SBram Moolenaar  set nostartofline
1131eb992cb9SBram Moolenaar  call feedkeys("A\<C-ScrollWheelDown>\<esc>", 'tnix')
1132eb992cb9SBram Moolenaar  call assert_equal([0, 6, 1, 0], getpos('.'))
1133eb992cb9SBram Moolenaar  call feedkeys("A\<LeftMouse>\<esc>", 'tnix')
1134eb992cb9SBram Moolenaar  call assert_equal([0, 6, 1, 0], getpos('.'))
1135eb992cb9SBram Moolenaar  call feedkeys("A\<RightMouse>\<esc>", 'tnix')
1136eb992cb9SBram Moolenaar  call assert_equal([0, 6, 1, 0], getpos('.'))
1137eb992cb9SBram Moolenaar  call cursor(1, 100)
1138eb992cb9SBram Moolenaar  norm! zt
1139eb992cb9SBram Moolenaar  " this should move by a screen up, but when the test
1140eb992cb9SBram Moolenaar  " is run, it moves up to the top of the buffer...
1141eb992cb9SBram Moolenaar  call feedkeys("A\<ScrollWheelUp>\<esc>", 'tnix')
1142eb992cb9SBram Moolenaar  call assert_equal([0, 1, 1, 0], getpos('.'))
1143eb992cb9SBram Moolenaar  call cursor(1, 30)
1144eb992cb9SBram Moolenaar  norm! zt
1145eb992cb9SBram Moolenaar  call feedkeys("A\<S-ScrollWheelUp>\<esc>", 'tnix')
1146eb992cb9SBram Moolenaar  call assert_equal([0, 1, 1, 0], getpos('.'))
1147eb992cb9SBram Moolenaar  call cursor(1, 30)
1148eb992cb9SBram Moolenaar  norm! zt
1149eb992cb9SBram Moolenaar  call feedkeys("A\<C-ScrollWheelUp>\<esc>", 'tnix')
1150eb992cb9SBram Moolenaar  call assert_equal([0, 1, 1, 0], getpos('.'))
1151eb992cb9SBram Moolenaar  %d
1152eb992cb9SBram Moolenaar  call setline(1, repeat(["12345678901234567890"], 100))
1153eb992cb9SBram Moolenaar  call cursor(2, 1)
1154eb992cb9SBram Moolenaar  call feedkeys("A\<ScrollWheelRight>\<esc>", 'tnix')
1155eb992cb9SBram Moolenaar  call assert_equal([0, 2, 20, 0], getpos('.'))
1156eb992cb9SBram Moolenaar  call feedkeys("A\<ScrollWheelLeft>\<esc>", 'tnix')
1157eb992cb9SBram Moolenaar  call assert_equal([0, 2, 20, 0], getpos('.'))
1158eb992cb9SBram Moolenaar  call feedkeys("A\<S-ScrollWheelRight>\<esc>", 'tnix')
1159eb992cb9SBram Moolenaar  call assert_equal([0, 2, 20, 0], getpos('.'))
1160eb992cb9SBram Moolenaar  call feedkeys("A\<S-ScrollWheelLeft>\<esc>", 'tnix')
1161eb992cb9SBram Moolenaar  call assert_equal([0, 2, 20, 0], getpos('.'))
1162eb992cb9SBram Moolenaar  call feedkeys("A\<C-ScrollWheelRight>\<esc>", 'tnix')
1163eb992cb9SBram Moolenaar  call assert_equal([0, 2, 20, 0], getpos('.'))
1164eb992cb9SBram Moolenaar  call feedkeys("A\<C-ScrollWheelLeft>\<esc>", 'tnix')
1165eb992cb9SBram Moolenaar  call assert_equal([0, 2, 20, 0], getpos('.'))
1166eb992cb9SBram Moolenaar  set mouse& startofline
1167eb992cb9SBram Moolenaar  bw!
1168eb992cb9SBram Moolenaarendfunc
1169eb992cb9SBram Moolenaar
11701e115360SBram Moolenaarfunc Test_edit_PAGEUP_PAGEDOWN()
1171eb992cb9SBram Moolenaar  10new
1172eb992cb9SBram Moolenaar  call setline(1, repeat(['abc def ghi'], 30))
1173eb992cb9SBram Moolenaar  call cursor(1, 1)
1174eb992cb9SBram Moolenaar  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1175eb992cb9SBram Moolenaar  call assert_equal([0, 9, 1, 0], getpos('.'))
1176eb992cb9SBram Moolenaar  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1177eb992cb9SBram Moolenaar  call assert_equal([0, 17, 1, 0], getpos('.'))
1178eb992cb9SBram Moolenaar  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1179eb992cb9SBram Moolenaar  call assert_equal([0, 25, 1, 0], getpos('.'))
1180eb992cb9SBram Moolenaar  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1181eb992cb9SBram Moolenaar  call assert_equal([0, 30, 1, 0], getpos('.'))
1182eb992cb9SBram Moolenaar  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1183eb992cb9SBram Moolenaar  call assert_equal([0, 30, 1, 0], getpos('.'))
1184eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1185eb992cb9SBram Moolenaar  call assert_equal([0, 29, 1, 0], getpos('.'))
1186eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1187eb992cb9SBram Moolenaar  call assert_equal([0, 21, 1, 0], getpos('.'))
1188eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1189eb992cb9SBram Moolenaar  call assert_equal([0, 13, 1, 0], getpos('.'))
1190eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1191eb992cb9SBram Moolenaar  call assert_equal([0, 5, 1, 0], getpos('.'))
1192eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1193eb992cb9SBram Moolenaar  call assert_equal([0, 5, 11, 0], getpos('.'))
1194eb992cb9SBram Moolenaar  " <S-Up> is the same as <PageUp>
1195eb992cb9SBram Moolenaar  " <S-Down> is the same as <PageDown>
1196eb992cb9SBram Moolenaar  call cursor(1, 1)
1197eb992cb9SBram Moolenaar  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1198eb992cb9SBram Moolenaar  call assert_equal([0, 9, 1, 0], getpos('.'))
1199eb992cb9SBram Moolenaar  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1200eb992cb9SBram Moolenaar  call assert_equal([0, 17, 1, 0], getpos('.'))
1201eb992cb9SBram Moolenaar  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1202eb992cb9SBram Moolenaar  call assert_equal([0, 25, 1, 0], getpos('.'))
1203eb992cb9SBram Moolenaar  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1204eb992cb9SBram Moolenaar  call assert_equal([0, 30, 1, 0], getpos('.'))
1205eb992cb9SBram Moolenaar  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1206eb992cb9SBram Moolenaar  call assert_equal([0, 30, 1, 0], getpos('.'))
1207eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1208eb992cb9SBram Moolenaar  call assert_equal([0, 29, 1, 0], getpos('.'))
1209eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1210eb992cb9SBram Moolenaar  call assert_equal([0, 21, 1, 0], getpos('.'))
1211eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1212eb992cb9SBram Moolenaar  call assert_equal([0, 13, 1, 0], getpos('.'))
1213eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1214eb992cb9SBram Moolenaar  call assert_equal([0, 5, 1, 0], getpos('.'))
1215eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1216eb992cb9SBram Moolenaar  call assert_equal([0, 5, 11, 0], getpos('.'))
1217eb992cb9SBram Moolenaar  set nostartofline
1218eb992cb9SBram Moolenaar  call cursor(30, 11)
1219eb992cb9SBram Moolenaar  norm! zt
1220eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1221eb992cb9SBram Moolenaar  call assert_equal([0, 29, 11, 0], getpos('.'))
1222eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1223eb992cb9SBram Moolenaar  call assert_equal([0, 21, 11, 0], getpos('.'))
1224eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1225eb992cb9SBram Moolenaar  call assert_equal([0, 13, 11, 0], getpos('.'))
1226eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1227eb992cb9SBram Moolenaar  call assert_equal([0, 5, 11, 0], getpos('.'))
1228eb992cb9SBram Moolenaar  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1229eb992cb9SBram Moolenaar  call assert_equal([0, 5, 11, 0], getpos('.'))
1230eb992cb9SBram Moolenaar  call cursor(1, 1)
1231eb992cb9SBram Moolenaar  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1232eb992cb9SBram Moolenaar  call assert_equal([0, 9, 11, 0], getpos('.'))
1233eb992cb9SBram Moolenaar  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1234eb992cb9SBram Moolenaar  call assert_equal([0, 17, 11, 0], getpos('.'))
1235eb992cb9SBram Moolenaar  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1236eb992cb9SBram Moolenaar  call assert_equal([0, 25, 11, 0], getpos('.'))
1237eb992cb9SBram Moolenaar  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1238eb992cb9SBram Moolenaar  call assert_equal([0, 30, 11, 0], getpos('.'))
1239eb992cb9SBram Moolenaar  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1240eb992cb9SBram Moolenaar  call assert_equal([0, 30, 11, 0], getpos('.'))
1241eb992cb9SBram Moolenaar  " <S-Up> is the same as <PageUp>
1242eb992cb9SBram Moolenaar  " <S-Down> is the same as <PageDown>
1243eb992cb9SBram Moolenaar  call cursor(30, 11)
1244eb992cb9SBram Moolenaar  norm! zt
1245eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1246eb992cb9SBram Moolenaar  call assert_equal([0, 29, 11, 0], getpos('.'))
1247eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1248eb992cb9SBram Moolenaar  call assert_equal([0, 21, 11, 0], getpos('.'))
1249eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1250eb992cb9SBram Moolenaar  call assert_equal([0, 13, 11, 0], getpos('.'))
1251eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1252eb992cb9SBram Moolenaar  call assert_equal([0, 5, 11, 0], getpos('.'))
1253eb992cb9SBram Moolenaar  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1254eb992cb9SBram Moolenaar  call assert_equal([0, 5, 11, 0], getpos('.'))
1255eb992cb9SBram Moolenaar  call cursor(1, 1)
1256eb992cb9SBram Moolenaar  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1257eb992cb9SBram Moolenaar  call assert_equal([0, 9, 11, 0], getpos('.'))
1258eb992cb9SBram Moolenaar  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1259eb992cb9SBram Moolenaar  call assert_equal([0, 17, 11, 0], getpos('.'))
1260eb992cb9SBram Moolenaar  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1261eb992cb9SBram Moolenaar  call assert_equal([0, 25, 11, 0], getpos('.'))
1262eb992cb9SBram Moolenaar  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1263eb992cb9SBram Moolenaar  call assert_equal([0, 30, 11, 0], getpos('.'))
1264eb992cb9SBram Moolenaar  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1265eb992cb9SBram Moolenaar  call assert_equal([0, 30, 11, 0], getpos('.'))
1266eb992cb9SBram Moolenaar  bw!
1267eb992cb9SBram Moolenaarendfunc
1268eb992cb9SBram Moolenaar
12691e115360SBram Moolenaarfunc Test_edit_forbidden()
1270eb992cb9SBram Moolenaar  new
1271eb992cb9SBram Moolenaar  " 1) edit in the sandbox is not allowed
1272eb992cb9SBram Moolenaar  call setline(1, 'a')
1273eb992cb9SBram Moolenaar  com! Sandbox :sandbox call feedkeys("i\<del>\<esc>", 'tnix')
1274eb992cb9SBram Moolenaar  call assert_fails(':Sandbox', 'E48:')
1275eb992cb9SBram Moolenaar  com! Sandbox :sandbox exe "norm! i\<del>"
1276eb992cb9SBram Moolenaar  call assert_fails(':Sandbox', 'E48:')
1277eb992cb9SBram Moolenaar  delcom Sandbox
1278eb992cb9SBram Moolenaar  call assert_equal(['a'], getline(1,'$'))
1279eb992cb9SBram Moolenaar  " 2) edit with textlock set
1280eb992cb9SBram Moolenaar  fu! DoIt()
1281eb992cb9SBram Moolenaar    call feedkeys("i\<del>\<esc>", 'tnix')
1282eb992cb9SBram Moolenaar  endfu
1283eb992cb9SBram Moolenaar  au InsertCharPre <buffer> :call DoIt()
1284eb992cb9SBram Moolenaar  try
1285eb992cb9SBram Moolenaar    call feedkeys("ix\<esc>", 'tnix')
1286eb992cb9SBram Moolenaar    call assert_fails(1, 'textlock')
1287ff06f283SBram Moolenaar  catch /^Vim\%((\a\+)\)\=:E565/ " catch E565: not allowed here
1288eb992cb9SBram Moolenaar  endtry
1289eb992cb9SBram Moolenaar  " TODO: Might be a bug: should x really be inserted here
1290eb992cb9SBram Moolenaar  call assert_equal(['xa'], getline(1, '$'))
1291eb992cb9SBram Moolenaar  delfu DoIt
1292eb992cb9SBram Moolenaar  try
1293eb992cb9SBram Moolenaar    call feedkeys("ix\<esc>", 'tnix')
1294eb992cb9SBram Moolenaar    call assert_fails(1, 'unknown function')
1295eb992cb9SBram Moolenaar  catch /^Vim\%((\a\+)\)\=:E117/ " catch E117: unknown function
1296eb992cb9SBram Moolenaar  endtry
1297eb992cb9SBram Moolenaar  au! InsertCharPre
1298eb992cb9SBram Moolenaar  " 3) edit when completion is shown
1299eb992cb9SBram Moolenaar  fun! Complete(findstart, base)
1300eb992cb9SBram Moolenaar    if a:findstart
1301eb992cb9SBram Moolenaar      return col('.')
1302eb992cb9SBram Moolenaar    else
1303eb992cb9SBram Moolenaar      call feedkeys("i\<del>\<esc>", 'tnix')
1304eb992cb9SBram Moolenaar      return []
1305eb992cb9SBram Moolenaar    endif
1306eb992cb9SBram Moolenaar  endfun
1307eb992cb9SBram Moolenaar  set completefunc=Complete
1308eb992cb9SBram Moolenaar  try
1309eb992cb9SBram Moolenaar    call feedkeys("i\<c-x>\<c-u>\<esc>", 'tnix')
1310eb992cb9SBram Moolenaar    call assert_fails(1, 'change in complete function')
1311ff06f283SBram Moolenaar  catch /^Vim\%((\a\+)\)\=:E565/ " catch E565
1312eb992cb9SBram Moolenaar  endtry
1313eb992cb9SBram Moolenaar  delfu Complete
1314eb992cb9SBram Moolenaar  set completefunc=
1315eb992cb9SBram Moolenaar  if has("rightleft") && exists("+fkmap")
1316eb992cb9SBram Moolenaar    " 4) 'R' when 'fkmap' and 'revins' is set.
1317eb992cb9SBram Moolenaar    set revins fkmap
1318eb992cb9SBram Moolenaar    try
1319eb992cb9SBram Moolenaar      normal Ri
1320eb992cb9SBram Moolenaar      call assert_fails(1, "R with 'fkmap' and 'ri' set")
1321eb992cb9SBram Moolenaar    catch
1322eb992cb9SBram Moolenaar    finally
1323eb992cb9SBram Moolenaar      set norevins nofkmap
1324eb992cb9SBram Moolenaar    endtry
1325eb992cb9SBram Moolenaar  endif
1326eb992cb9SBram Moolenaar  bw!
1327eb992cb9SBram Moolenaarendfunc
1328eb992cb9SBram Moolenaar
13291e115360SBram Moolenaarfunc Test_edit_rightleft()
1330eb992cb9SBram Moolenaar  " Cursor in rightleft mode moves differently
1331845e0ee5SBram Moolenaar  CheckFeature rightleft
1332eb992cb9SBram Moolenaar  call NewWindow(10, 20)
1333eb992cb9SBram Moolenaar  call setline(1, ['abc', 'def', 'ghi'])
1334eb992cb9SBram Moolenaar  call cursor(1, 2)
1335eb992cb9SBram Moolenaar  set rightleft
1336eb992cb9SBram Moolenaar  " Screen looks as expected
1337eb992cb9SBram Moolenaar  let lines = ScreenLines([1, 4], winwidth(0))
1338eb992cb9SBram Moolenaar  let expect = [
1339eb992cb9SBram Moolenaar        \"                 cba",
1340eb992cb9SBram Moolenaar        \"                 fed",
1341eb992cb9SBram Moolenaar        \"                 ihg",
1342eb992cb9SBram Moolenaar        \"                   ~"]
1343eb992cb9SBram Moolenaar  call assert_equal(join(expect, "\n"), join(lines, "\n"))
1344eb992cb9SBram Moolenaar  " 2) right moves to the left
1345eb992cb9SBram Moolenaar  call feedkeys("i\<right>\<esc>x", 'txin')
1346eb992cb9SBram Moolenaar  call assert_equal(['bc', 'def', 'ghi'], getline(1,'$'))
1347eb992cb9SBram Moolenaar  call cursor(1, 2)
1348eb992cb9SBram Moolenaar  call feedkeys("i\<s-right>\<esc>", 'txin')
1349eb992cb9SBram Moolenaar  call cursor(1, 2)
1350eb992cb9SBram Moolenaar  call feedkeys("i\<c-right>\<esc>", 'txin')
1351eb992cb9SBram Moolenaar  " Screen looks as expected
1352eb992cb9SBram Moolenaar  let lines = ScreenLines([1, 4], winwidth(0))
1353eb992cb9SBram Moolenaar  let expect = [
1354eb992cb9SBram Moolenaar        \"                  cb",
1355eb992cb9SBram Moolenaar        \"                 fed",
1356eb992cb9SBram Moolenaar        \"                 ihg",
1357eb992cb9SBram Moolenaar        \"                   ~"]
1358eb992cb9SBram Moolenaar  call assert_equal(join(expect, "\n"), join(lines, "\n"))
1359eb992cb9SBram Moolenaar  " 2) left moves to the right
1360eb992cb9SBram Moolenaar  call setline(1, ['abc', 'def', 'ghi'])
1361eb992cb9SBram Moolenaar  call cursor(1, 2)
1362eb992cb9SBram Moolenaar  call feedkeys("i\<left>\<esc>x", 'txin')
1363eb992cb9SBram Moolenaar  call assert_equal(['ac', 'def', 'ghi'], getline(1,'$'))
1364eb992cb9SBram Moolenaar  call cursor(1, 2)
1365eb992cb9SBram Moolenaar  call feedkeys("i\<s-left>\<esc>", 'txin')
1366eb992cb9SBram Moolenaar  call cursor(1, 2)
1367eb992cb9SBram Moolenaar  call feedkeys("i\<c-left>\<esc>", 'txin')
1368eb992cb9SBram Moolenaar  " Screen looks as expected
1369eb992cb9SBram Moolenaar  let lines = ScreenLines([1, 4], winwidth(0))
1370eb992cb9SBram Moolenaar  let expect = [
1371eb992cb9SBram Moolenaar        \"                  ca",
1372eb992cb9SBram Moolenaar        \"                 fed",
1373eb992cb9SBram Moolenaar        \"                 ihg",
1374eb992cb9SBram Moolenaar        \"                   ~"]
1375eb992cb9SBram Moolenaar  call assert_equal(join(expect, "\n"), join(lines, "\n"))
1376845e0ee5SBram Moolenaar  %d _
1377845e0ee5SBram Moolenaar  call test_override('redraw_flag', 1)
1378845e0ee5SBram Moolenaar  call test_override('char_avail', 1)
1379845e0ee5SBram Moolenaar  call feedkeys("a\<C-V>x41", "xt")
1380845e0ee5SBram Moolenaar  redraw!
1381845e0ee5SBram Moolenaar  call assert_equal(repeat(' ', 19) .. 'A', Screenline(1))
1382845e0ee5SBram Moolenaar  call test_override('ALL', 0)
1383eb992cb9SBram Moolenaar  set norightleft
1384eb992cb9SBram Moolenaar  bw!
1385eb992cb9SBram Moolenaarendfunc
1386658a3a2cSBram Moolenaar
1387658a3a2cSBram Moolenaarfunc Test_edit_complete_very_long_name()
13889b81079dSBram Moolenaar  " Long directory names only work on Unix.
13896d91bcb4SBram Moolenaar  CheckUnix
139015ecbd6fSBram Moolenaar
139115ecbd6fSBram Moolenaar  let dirname = getcwd() . "/Xdir"
139215ecbd6fSBram Moolenaar  let longdirname = dirname . repeat('/' . repeat('d', 255), 4)
139315ecbd6fSBram Moolenaar  try
139415ecbd6fSBram Moolenaar    call mkdir(longdirname, 'p')
139515ecbd6fSBram Moolenaar  catch /E739:/
139615ecbd6fSBram Moolenaar    " Long directory name probably not supported.
139715ecbd6fSBram Moolenaar    call delete(dirname, 'rf')
139815ecbd6fSBram Moolenaar    return
139915ecbd6fSBram Moolenaar  endtry
140015ecbd6fSBram Moolenaar
1401f8191c5fSBram Moolenaar  " Try to get the Vim window position before setting 'columns', so that we can
1402f8191c5fSBram Moolenaar  " move the window back to where it was.
1403ba6ec182SBram Moolenaar  let winposx = getwinposx()
1404ba6ec182SBram Moolenaar  let winposy = getwinposy()
1405f8191c5fSBram Moolenaar
1406f8191c5fSBram Moolenaar  if winposx >= 0 && winposy >= 0 && !has('gui_running')
1407f8191c5fSBram Moolenaar    " We did get the window position, but xterm may report the wrong numbers.
1408f8191c5fSBram Moolenaar    " Move the window to the reported position and compute any offset.
1409f8191c5fSBram Moolenaar    exe 'winpos ' . winposx . ' ' . winposy
1410f8191c5fSBram Moolenaar    sleep 100m
1411f8191c5fSBram Moolenaar    let x = getwinposx()
1412f8191c5fSBram Moolenaar    if x >= 0
1413f8191c5fSBram Moolenaar      let winposx += winposx - x
1414f8191c5fSBram Moolenaar    endif
1415f8191c5fSBram Moolenaar    let y = getwinposy()
1416f8191c5fSBram Moolenaar    if y >= 0
1417f8191c5fSBram Moolenaar      let winposy += winposy - y
1418f8191c5fSBram Moolenaar    endif
1419f8191c5fSBram Moolenaar  endif
1420f8191c5fSBram Moolenaar
1421658a3a2cSBram Moolenaar  let save_columns = &columns
142215ecbd6fSBram Moolenaar  " Need at least about 1100 columns to reproduce the problem.
1423ba6ec182SBram Moolenaar  set columns=2000
1424658a3a2cSBram Moolenaar  set noswapfile
1425ba6ec182SBram Moolenaar
1426658a3a2cSBram Moolenaar  let longfilename = longdirname . '/' . repeat('a', 255)
1427658a3a2cSBram Moolenaar  call writefile(['Totum', 'Table'], longfilename)
1428658a3a2cSBram Moolenaar  new
1429658a3a2cSBram Moolenaar  exe "next Xfile " . longfilename
1430658a3a2cSBram Moolenaar  exe "normal iT\<C-N>"
1431658a3a2cSBram Moolenaar
1432658a3a2cSBram Moolenaar  bwipe!
1433658a3a2cSBram Moolenaar  exe 'bwipe! ' . longfilename
1434658a3a2cSBram Moolenaar  call delete(dirname, 'rf')
1435658a3a2cSBram Moolenaar  let &columns = save_columns
1436ba6ec182SBram Moolenaar  if winposx >= 0 && winposy >= 0
1437ba6ec182SBram Moolenaar    exe 'winpos ' . winposx . ' ' . winposy
1438ba6ec182SBram Moolenaar  endif
1439658a3a2cSBram Moolenaar  set swapfile&
1440658a3a2cSBram Moolenaarendfunc
1441ff930cadSBram Moolenaar
14422c8c681bSBram Moolenaarfunc Test_edit_backtick()
14432c8c681bSBram Moolenaar  next a\`b c
14442c8c681bSBram Moolenaar  call assert_equal('a`b', expand('%'))
14452c8c681bSBram Moolenaar  next
14462c8c681bSBram Moolenaar  call assert_equal('c', expand('%'))
14472c8c681bSBram Moolenaar  call assert_equal('a\`b c', expand('##'))
14482c8c681bSBram Moolenaarendfunc
14492c8c681bSBram Moolenaar
1450ff930cadSBram Moolenaarfunc Test_edit_quit()
1451ff930cadSBram Moolenaar  edit foo.txt
1452ff930cadSBram Moolenaar  split
1453ff930cadSBram Moolenaar  new
1454ff930cadSBram Moolenaar  call setline(1, 'hello')
1455ff930cadSBram Moolenaar  3wincmd w
1456ff930cadSBram Moolenaar  redraw!
1457ff930cadSBram Moolenaar  call assert_fails('1q', 'E37:')
1458ff930cadSBram Moolenaar  bwipe! foo.txt
1459ff930cadSBram Moolenaar  only
1460ff930cadSBram Moolenaarendfunc
1461ff930cadSBram Moolenaar
1462adb8fbecSBram Moolenaarfunc Test_edit_alt()
1463adb8fbecSBram Moolenaar  " Keeping the cursor line didn't happen when the first line has indent.
1464adb8fbecSBram Moolenaar  new
1465adb8fbecSBram Moolenaar  call setline(1, ['  one', 'two', 'three'])
1466adb8fbecSBram Moolenaar  w XAltFile
1467adb8fbecSBram Moolenaar  $
1468adb8fbecSBram Moolenaar  call assert_equal(3, line('.'))
1469adb8fbecSBram Moolenaar  e Xother
1470adb8fbecSBram Moolenaar  e #
1471adb8fbecSBram Moolenaar  call assert_equal(3, line('.'))
1472adb8fbecSBram Moolenaar
1473adb8fbecSBram Moolenaar  bwipe XAltFile
1474adb8fbecSBram Moolenaar  call delete('XAltFile')
1475adb8fbecSBram Moolenaarendfunc
14764dbc2627SBram Moolenaar
1477db93495dSBram Moolenaarfunc Test_edit_InsertLeave()
14784dbc2627SBram Moolenaar  new
1479b53e13a9SBram Moolenaar  au InsertLeavePre * let g:did_au_pre = 1
14804dbc2627SBram Moolenaar  au InsertLeave * let g:did_au = 1
1481b53e13a9SBram Moolenaar  let g:did_au_pre = 0
14824dbc2627SBram Moolenaar  let g:did_au = 0
14834dbc2627SBram Moolenaar  call feedkeys("afoo\<Esc>", 'tx')
1484b53e13a9SBram Moolenaar  call assert_equal(1, g:did_au_pre)
14854dbc2627SBram Moolenaar  call assert_equal(1, g:did_au)
14864dbc2627SBram Moolenaar  call assert_equal('foo', getline(1))
14874dbc2627SBram Moolenaar
1488b53e13a9SBram Moolenaar  let g:did_au_pre = 0
14894dbc2627SBram Moolenaar  let g:did_au = 0
14904dbc2627SBram Moolenaar  call feedkeys("Sbar\<C-C>", 'tx')
1491b53e13a9SBram Moolenaar  call assert_equal(1, g:did_au_pre)
14924dbc2627SBram Moolenaar  call assert_equal(0, g:did_au)
14934dbc2627SBram Moolenaar  call assert_equal('bar', getline(1))
14944dbc2627SBram Moolenaar
14954dbc2627SBram Moolenaar  inoremap x xx<Esc>
1496b53e13a9SBram Moolenaar  let g:did_au_pre = 0
14974dbc2627SBram Moolenaar  let g:did_au = 0
14984dbc2627SBram Moolenaar  call feedkeys("Saax", 'tx')
1499b53e13a9SBram Moolenaar  call assert_equal(1, g:did_au_pre)
15004dbc2627SBram Moolenaar  call assert_equal(1, g:did_au)
15014dbc2627SBram Moolenaar  call assert_equal('aaxx', getline(1))
15024dbc2627SBram Moolenaar
15034dbc2627SBram Moolenaar  inoremap x xx<C-C>
1504b53e13a9SBram Moolenaar  let g:did_au_pre = 0
15054dbc2627SBram Moolenaar  let g:did_au = 0
15064dbc2627SBram Moolenaar  call feedkeys("Sbbx", 'tx')
1507b53e13a9SBram Moolenaar  call assert_equal(1, g:did_au_pre)
15084dbc2627SBram Moolenaar  call assert_equal(0, g:did_au)
15094dbc2627SBram Moolenaar  call assert_equal('bbxx', getline(1))
15104dbc2627SBram Moolenaar
15114dbc2627SBram Moolenaar  bwipe!
1512b53e13a9SBram Moolenaar  au! InsertLeave InsertLeavePre
15134dbc2627SBram Moolenaar  iunmap x
15144dbc2627SBram Moolenaarendfunc
1515c6b37db1SBram Moolenaar
1516db93495dSBram Moolenaarfunc Test_edit_InsertLeave_undo()
1517db93495dSBram Moolenaar  new XtestUndo
1518db93495dSBram Moolenaar  set undofile
1519db93495dSBram Moolenaar  au InsertLeave * wall
1520db93495dSBram Moolenaar  exe "normal ofoo\<Esc>"
1521db93495dSBram Moolenaar  call assert_equal(2, line('$'))
1522db93495dSBram Moolenaar  normal u
1523db93495dSBram Moolenaar  call assert_equal(1, line('$'))
1524db93495dSBram Moolenaar
1525db93495dSBram Moolenaar  bwipe!
1526db93495dSBram Moolenaar  au! InsertLeave
1527db93495dSBram Moolenaar  call delete('XtestUndo')
1528b340baedSBram Moolenaar  call delete(undofile('XtestUndo'))
1529db93495dSBram Moolenaar  set undofile&
1530db93495dSBram Moolenaarendfunc
1531db93495dSBram Moolenaar
1532c6b37db1SBram Moolenaar" Test for inserting characters using CTRL-V followed by a number.
1533c6b37db1SBram Moolenaarfunc Test_edit_special_chars()
1534c6b37db1SBram Moolenaar  new
1535c6b37db1SBram Moolenaar
1536c6b37db1SBram Moolenaar  if has("ebcdic")
1537c6b37db1SBram Moolenaar    let t = "o\<C-V>193\<C-V>xc2\<C-V>o303 \<C-V>90a\<C-V>xfg\<C-V>o578\<Esc>"
1538c6b37db1SBram Moolenaar  else
1539c6b37db1SBram Moolenaar    let t = "o\<C-V>65\<C-V>x42\<C-V>o103 \<C-V>33a\<C-V>xfg\<C-V>o78\<Esc>"
1540c6b37db1SBram Moolenaar  endif
1541c6b37db1SBram Moolenaar
1542c6b37db1SBram Moolenaar  exe "normal " . t
1543c6b37db1SBram Moolenaar  call assert_equal("ABC !a\<C-O>g\<C-G>8", getline(2))
1544c6b37db1SBram Moolenaar
1545c6b37db1SBram Moolenaar  close!
1546c6b37db1SBram Moolenaarendfunc
15478d3b5108SBram Moolenaar
15488d3b5108SBram Moolenaarfunc Test_edit_startinsert()
15498d3b5108SBram Moolenaar  new
15508d3b5108SBram Moolenaar  set backspace+=start
15518d3b5108SBram Moolenaar  call setline(1, 'foobar')
15528d3b5108SBram Moolenaar  call feedkeys("A\<C-U>\<Esc>", 'xt')
15538d3b5108SBram Moolenaar  call assert_equal('', getline(1))
15548d3b5108SBram Moolenaar
15558d3b5108SBram Moolenaar  call setline(1, 'foobar')
15568d3b5108SBram Moolenaar  call feedkeys(":startinsert!\<CR>\<C-U>\<Esc>", 'xt')
15578d3b5108SBram Moolenaar  call assert_equal('', getline(1))
15588d3b5108SBram Moolenaar
15598d3b5108SBram Moolenaar  set backspace&
15608d3b5108SBram Moolenaar  bwipe!
15618d3b5108SBram Moolenaarendfunc
1562177c9f2fSBram Moolenaar
1563bc2b71d4SBram Moolenaar" Test for :startreplace and :startgreplace
1564bc2b71d4SBram Moolenaarfunc Test_edit_startreplace()
1565bc2b71d4SBram Moolenaar  new
1566bc2b71d4SBram Moolenaar  call setline(1, 'abc')
1567bc2b71d4SBram Moolenaar  call feedkeys("l:startreplace\<CR>xyz\e", 'xt')
1568bc2b71d4SBram Moolenaar  call assert_equal('axyz', getline(1))
1569bc2b71d4SBram Moolenaar  call feedkeys("0:startreplace!\<CR>abc\e", 'xt')
1570bc2b71d4SBram Moolenaar  call assert_equal('axyzabc', getline(1))
1571bc2b71d4SBram Moolenaar  call setline(1, "a\tb")
1572bc2b71d4SBram Moolenaar  call feedkeys("0l:startgreplace\<CR>xyz\e", 'xt')
1573bc2b71d4SBram Moolenaar  call assert_equal("axyz\tb", getline(1))
1574bc2b71d4SBram Moolenaar  call feedkeys("0i\<C-R>=execute('startreplace')\<CR>12\e", 'xt')
1575bc2b71d4SBram Moolenaar  call assert_equal("12axyz\tb", getline(1))
1576bc2b71d4SBram Moolenaar  close!
1577bc2b71d4SBram Moolenaarendfunc
1578bc2b71d4SBram Moolenaar
1579177c9f2fSBram Moolenaarfunc Test_edit_noesckeys()
1580215ba3b6SBram Moolenaar  CheckNotGui
1581177c9f2fSBram Moolenaar  new
1582177c9f2fSBram Moolenaar
1583177c9f2fSBram Moolenaar  " <Left> moves cursor when 'esckeys' is set
1584177c9f2fSBram Moolenaar  exe "set t_kl=\<Esc>OD"
1585177c9f2fSBram Moolenaar  set esckeys
1586177c9f2fSBram Moolenaar  call feedkeys("axyz\<Esc>ODX", "xt")
1587177c9f2fSBram Moolenaar  call assert_equal("xyXz", getline(1))
1588177c9f2fSBram Moolenaar
1589177c9f2fSBram Moolenaar  " <Left> exits Insert mode when 'esckeys' is off
1590177c9f2fSBram Moolenaar  set noesckeys
1591177c9f2fSBram Moolenaar  call setline(1, '')
1592177c9f2fSBram Moolenaar  call feedkeys("axyz\<Esc>ODX", "xt")
1593177c9f2fSBram Moolenaar  call assert_equal(["DX", "xyz"], getline(1, 2))
1594177c9f2fSBram Moolenaar
1595177c9f2fSBram Moolenaar  bwipe!
1596177c9f2fSBram Moolenaar  set esckeys
1597177c9f2fSBram Moolenaarendfunc
1598bc2b71d4SBram Moolenaar
15991671f448SBram Moolenaar" Test for running an invalid ex command in insert mode using CTRL-O
16001671f448SBram Moolenaarfunc Test_edit_ctrl_o_invalid_cmd()
16011671f448SBram Moolenaar  new
16021671f448SBram Moolenaar  set showmode showcmd
1603b340baedSBram Moolenaar  " Avoid a sleep of 3 seconds. Zero might have side effects.
1604b340baedSBram Moolenaar  call test_override('ui_delay', 50)
16051671f448SBram Moolenaar  let caught_e492 = 0
16061671f448SBram Moolenaar  try
16071671f448SBram Moolenaar    call feedkeys("i\<C-O>:invalid\<CR>abc\<Esc>", "xt")
16081671f448SBram Moolenaar  catch /E492:/
16091671f448SBram Moolenaar    let caught_e492 = 1
16101671f448SBram Moolenaar  endtry
16111671f448SBram Moolenaar  call assert_equal(1, caught_e492)
16121671f448SBram Moolenaar  call assert_equal('abc', getline(1))
16131671f448SBram Moolenaar  set showmode& showcmd&
1614b340baedSBram Moolenaar  call test_override('ui_delay', 0)
16151671f448SBram Moolenaar  close!
16161671f448SBram Moolenaarendfunc
16171671f448SBram Moolenaar
1618b340baedSBram Moolenaar" Test for editing a file with a very long name
1619b340baedSBram Moolenaarfunc Test_edit_illegal_filename()
1620b340baedSBram Moolenaar  CheckEnglish
1621b340baedSBram Moolenaar  new
1622b340baedSBram Moolenaar  redir => msg
1623b340baedSBram Moolenaar  exe 'edit ' . repeat('f', 5000)
1624b340baedSBram Moolenaar  redir END
1625b340baedSBram Moolenaar  call assert_match("Illegal file name$", split(msg, "\n")[0])
1626b340baedSBram Moolenaar  close!
1627b340baedSBram Moolenaarendfunc
1628b340baedSBram Moolenaar
1629c8fe645cSBram Moolenaar" Test for editing a directory
1630c8fe645cSBram Moolenaarfunc Test_edit_is_a_directory()
1631c8fe645cSBram Moolenaar  CheckEnglish
1632c8fe645cSBram Moolenaar  let dirname = getcwd() . "/Xdir"
1633c8fe645cSBram Moolenaar  call mkdir(dirname, 'p')
1634c8fe645cSBram Moolenaar
1635c8fe645cSBram Moolenaar  new
1636c8fe645cSBram Moolenaar  redir => msg
1637c8fe645cSBram Moolenaar  exe 'edit' dirname
1638c8fe645cSBram Moolenaar  redir END
1639c8fe645cSBram Moolenaar  call assert_match("is a directory$", split(msg, "\n")[0])
1640c8fe645cSBram Moolenaar  bwipe!
1641c8fe645cSBram Moolenaar
1642c8fe645cSBram Moolenaar  let dirname .= '/'
1643c8fe645cSBram Moolenaar
1644c8fe645cSBram Moolenaar  new
1645c8fe645cSBram Moolenaar  redir => msg
1646c8fe645cSBram Moolenaar  exe 'edit' dirname
1647c8fe645cSBram Moolenaar  redir END
1648c8fe645cSBram Moolenaar  call assert_match("is a directory$", split(msg, "\n")[0])
1649c8fe645cSBram Moolenaar  bwipe!
1650c8fe645cSBram Moolenaar
1651c8fe645cSBram Moolenaar  call delete(dirname, 'rf')
1652c8fe645cSBram Moolenaarendfunc
1653c8fe645cSBram Moolenaar
1654b340baedSBram Moolenaar" Test for editing a file using invalid file encoding
1655b340baedSBram Moolenaarfunc Test_edit_invalid_encoding()
1656b340baedSBram Moolenaar  CheckEnglish
1657b340baedSBram Moolenaar  call writefile([], 'Xfile')
1658b340baedSBram Moolenaar  redir => msg
1659b340baedSBram Moolenaar  new ++enc=axbyc Xfile
1660b340baedSBram Moolenaar  redir END
1661b340baedSBram Moolenaar  call assert_match('\[NOT converted\]', msg)
1662b340baedSBram Moolenaar  call delete('Xfile')
1663b340baedSBram Moolenaar  close!
1664b340baedSBram Moolenaarendfunc
1665b340baedSBram Moolenaar
1666b340baedSBram Moolenaar" Test for the "charconvert" option
1667b340baedSBram Moolenaarfunc Test_edit_charconvert()
1668b340baedSBram Moolenaar  CheckEnglish
1669b340baedSBram Moolenaar  call writefile(['one', 'two'], 'Xfile')
1670b340baedSBram Moolenaar
1671b340baedSBram Moolenaar  " set 'charconvert' to a non-existing function
1672b340baedSBram Moolenaar  set charconvert=NonExitingFunc()
1673b340baedSBram Moolenaar  new
1674b340baedSBram Moolenaar  let caught_e117 = v:false
1675b340baedSBram Moolenaar  try
1676b340baedSBram Moolenaar    redir => msg
1677b340baedSBram Moolenaar    edit ++enc=axbyc Xfile
1678b340baedSBram Moolenaar  catch /E117:/
1679b340baedSBram Moolenaar    let caught_e117 = v:true
1680b340baedSBram Moolenaar  finally
1681b340baedSBram Moolenaar    redir END
1682b340baedSBram Moolenaar  endtry
1683b340baedSBram Moolenaar  call assert_true(caught_e117)
1684b340baedSBram Moolenaar  call assert_equal(['one', 'two'], getline(1, '$'))
1685b340baedSBram Moolenaar  call assert_match("Conversion with 'charconvert' failed", msg)
1686b340baedSBram Moolenaar  close!
1687b340baedSBram Moolenaar  set charconvert&
1688b340baedSBram Moolenaar
1689b340baedSBram Moolenaar  " 'charconvert' function doesn't create a output file
1690b340baedSBram Moolenaar  func Cconv1()
1691b340baedSBram Moolenaar  endfunc
1692b340baedSBram Moolenaar  set charconvert=Cconv1()
1693b340baedSBram Moolenaar  new
1694b340baedSBram Moolenaar  redir => msg
1695b340baedSBram Moolenaar  edit ++enc=axbyc Xfile
1696b340baedSBram Moolenaar  redir END
1697b340baedSBram Moolenaar  call assert_equal(['one', 'two'], getline(1, '$'))
1698b340baedSBram Moolenaar  call assert_match("can't read output of 'charconvert'", msg)
1699b340baedSBram Moolenaar  close!
1700b340baedSBram Moolenaar  delfunc Cconv1
1701b340baedSBram Moolenaar  set charconvert&
1702b340baedSBram Moolenaar
1703b340baedSBram Moolenaar  " 'charconvert' function to convert to upper case
1704b340baedSBram Moolenaar  func Cconv2()
1705b340baedSBram Moolenaar    let data = readfile(v:fname_in)
1706b340baedSBram Moolenaar    call map(data, 'toupper(v:val)')
1707b340baedSBram Moolenaar    call writefile(data, v:fname_out)
1708b340baedSBram Moolenaar  endfunc
1709b340baedSBram Moolenaar  set charconvert=Cconv2()
1710b340baedSBram Moolenaar  new Xfile
1711b340baedSBram Moolenaar  write ++enc=ucase Xfile1
1712b340baedSBram Moolenaar  call assert_equal(['ONE', 'TWO'], readfile('Xfile1'))
1713b340baedSBram Moolenaar  call delete('Xfile1')
1714b340baedSBram Moolenaar  close!
1715b340baedSBram Moolenaar  delfunc Cconv2
1716b340baedSBram Moolenaar  set charconvert&
1717b340baedSBram Moolenaar
1718b340baedSBram Moolenaar  " 'charconvert' function removes the input file
1719b340baedSBram Moolenaar  func Cconv3()
1720b340baedSBram Moolenaar    call delete(v:fname_in)
1721b340baedSBram Moolenaar  endfunc
1722b340baedSBram Moolenaar  set charconvert=Cconv3()
1723b340baedSBram Moolenaar  new
1724b340baedSBram Moolenaar  call assert_fails('edit ++enc=lcase Xfile', 'E202:')
1725b340baedSBram Moolenaar  call assert_equal([''], getline(1, '$'))
1726b340baedSBram Moolenaar  close!
1727b340baedSBram Moolenaar  delfunc Cconv3
1728b340baedSBram Moolenaar  set charconvert&
1729b340baedSBram Moolenaar
1730b340baedSBram Moolenaar  call delete('Xfile')
1731b340baedSBram Moolenaarendfunc
1732b340baedSBram Moolenaar
1733b340baedSBram Moolenaar" Test for editing a file without read permission
1734b340baedSBram Moolenaarfunc Test_edit_file_no_read_perm()
1735b340baedSBram Moolenaar  CheckUnix
173617709e28SBram Moolenaar  CheckNotRoot
173717709e28SBram Moolenaar
1738b340baedSBram Moolenaar  call writefile(['one', 'two'], 'Xfile')
1739b340baedSBram Moolenaar  call setfperm('Xfile', '-w-------')
1740b340baedSBram Moolenaar  new
1741b340baedSBram Moolenaar  redir => msg
1742b340baedSBram Moolenaar  edit Xfile
1743b340baedSBram Moolenaar  redir END
1744b340baedSBram Moolenaar  call assert_equal(1, &readonly)
1745b340baedSBram Moolenaar  call assert_equal([''], getline(1, '$'))
1746b340baedSBram Moolenaar  call assert_match('\[Permission Denied\]', msg)
1747b340baedSBram Moolenaar  close!
1748b340baedSBram Moolenaar  call delete('Xfile')
1749b340baedSBram Moolenaarendfunc
1750b340baedSBram Moolenaar
1751845e0ee5SBram Moolenaar" Pressing escape in 'insertmode' should beep
1752845e0ee5SBram Moolenaarfunc Test_edit_insertmode_esc_beeps()
1753845e0ee5SBram Moolenaar  new
1754845e0ee5SBram Moolenaar  set insertmode
1755845e0ee5SBram Moolenaar  call assert_beeps("call feedkeys(\"one\<Esc>\", 'xt')")
1756845e0ee5SBram Moolenaar  set insertmode&
1757845e0ee5SBram Moolenaar  " unsupported CTRL-G command should beep in insert mode.
1758845e0ee5SBram Moolenaar  call assert_beeps("normal i\<C-G>l")
1759845e0ee5SBram Moolenaar  close!
1760845e0ee5SBram Moolenaarendfunc
1761845e0ee5SBram Moolenaar
1762845e0ee5SBram Moolenaar" Test for 'hkmap' and 'hkmapp'
1763845e0ee5SBram Moolenaarfunc Test_edit_hkmap()
1764845e0ee5SBram Moolenaar  CheckFeature rightleft
1765845e0ee5SBram Moolenaar  if has('win32') && !has('gui')
17666d91bcb4SBram Moolenaar    throw 'Skipped: fails on the MS-Windows terminal version'
1767845e0ee5SBram Moolenaar  endif
1768845e0ee5SBram Moolenaar  new
1769845e0ee5SBram Moolenaar
1770845e0ee5SBram Moolenaar  set revins hkmap
1771845e0ee5SBram Moolenaar  let str = 'abcdefghijklmnopqrstuvwxyz'
1772845e0ee5SBram Moolenaar  let str ..= 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'
1773845e0ee5SBram Moolenaar  let str ..= '`/'',.;'
1774845e0ee5SBram Moolenaar  call feedkeys('i' .. str, 'xt')
1775845e0ee5SBram Moolenaar  let expected = "óõú,.;"
1776845e0ee5SBram Moolenaar  let expected ..= "ZYXWVUTSRQPONMLKJIHGFEDCBA"
1777845e0ee5SBram Moolenaar  let expected ..= "æèñ'äåàãø/ôíîöêìçïéòë÷âáðù"
1778845e0ee5SBram Moolenaar  call assert_equal(expected, getline(1))
1779845e0ee5SBram Moolenaar
1780845e0ee5SBram Moolenaar  %d
1781845e0ee5SBram Moolenaar  set revins hkmap hkmapp
1782845e0ee5SBram Moolenaar  let str = 'abcdefghijklmnopqrstuvwxyz'
1783845e0ee5SBram Moolenaar  let str ..= 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'
1784845e0ee5SBram Moolenaar  call feedkeys('i' .. str, 'xt')
1785845e0ee5SBram Moolenaar  let expected = "õYXWVUTSRQóOïíLKJIHGFEDêBA"
1786845e0ee5SBram Moolenaar  let expected ..= "öòXùåèúæø'ôñðîì÷çéäâóǟãëáà"
1787845e0ee5SBram Moolenaar  call assert_equal(expected, getline(1))
1788845e0ee5SBram Moolenaar
1789845e0ee5SBram Moolenaar  set revins& hkmap& hkmapp&
1790845e0ee5SBram Moolenaar  close!
1791845e0ee5SBram Moolenaarendfunc
1792845e0ee5SBram Moolenaar
1793845e0ee5SBram Moolenaar" Test for 'allowrevins' and using CTRL-_ in insert mode
1794845e0ee5SBram Moolenaarfunc Test_edit_allowrevins()
1795845e0ee5SBram Moolenaar  CheckFeature rightleft
1796845e0ee5SBram Moolenaar  new
1797845e0ee5SBram Moolenaar  set allowrevins
1798845e0ee5SBram Moolenaar  call feedkeys("iABC\<C-_>DEF\<C-_>GHI", 'xt')
1799845e0ee5SBram Moolenaar  call assert_equal('ABCFEDGHI', getline(1))
1800845e0ee5SBram Moolenaar  set allowrevins&
1801845e0ee5SBram Moolenaar  close!
1802845e0ee5SBram Moolenaarendfunc
1803845e0ee5SBram Moolenaar
1804845e0ee5SBram Moolenaar" Test for inserting a register in insert mode using CTRL-R
1805845e0ee5SBram Moolenaarfunc Test_edit_insert_reg()
1806845e0ee5SBram Moolenaar  new
1807845e0ee5SBram Moolenaar  let g:Line = ''
1808845e0ee5SBram Moolenaar  func SaveFirstLine()
1809845e0ee5SBram Moolenaar    let g:Line = Screenline(1)
1810845e0ee5SBram Moolenaar    return 'r'
1811845e0ee5SBram Moolenaar  endfunc
1812845e0ee5SBram Moolenaar  inoremap <expr> <buffer> <F2> SaveFirstLine()
1813845e0ee5SBram Moolenaar  call test_override('redraw_flag', 1)
1814845e0ee5SBram Moolenaar  call test_override('char_avail', 1)
1815845e0ee5SBram Moolenaar  let @r = 'sample'
1816845e0ee5SBram Moolenaar  call feedkeys("a\<C-R>=SaveFirstLine()\<CR>", "xt")
1817845e0ee5SBram Moolenaar  call assert_equal('"', g:Line)
1818845e0ee5SBram Moolenaar  call test_override('ALL', 0)
1819845e0ee5SBram Moolenaar  close!
1820845e0ee5SBram Moolenaarendfunc
1821845e0ee5SBram Moolenaar
1822845e0ee5SBram Moolenaar" When a character is inserted at the last position of the last line in a
1823845e0ee5SBram Moolenaar" window, the window contents should be scrolled one line up. If the top line
1824845e0ee5SBram Moolenaar" is part of a fold, then the entire fold should be scrolled up.
1825845e0ee5SBram Moolenaarfunc Test_edit_lastline_scroll()
1826845e0ee5SBram Moolenaar  new
1827845e0ee5SBram Moolenaar  let h = winheight(0)
1828845e0ee5SBram Moolenaar  let lines = ['one', 'two', 'three']
1829845e0ee5SBram Moolenaar  let lines += repeat(['vim'], h - 4)
1830845e0ee5SBram Moolenaar  call setline(1, lines)
1831845e0ee5SBram Moolenaar  call setline(h, repeat('x', winwidth(0) - 1))
1832845e0ee5SBram Moolenaar  call feedkeys("GAx", 'xt')
1833845e0ee5SBram Moolenaar  redraw!
1834845e0ee5SBram Moolenaar  call assert_equal(h - 1, winline())
1835845e0ee5SBram Moolenaar  call assert_equal(2, line('w0'))
1836845e0ee5SBram Moolenaar
1837845e0ee5SBram Moolenaar  " scroll with a fold
1838845e0ee5SBram Moolenaar  1,2fold
1839845e0ee5SBram Moolenaar  normal gg
1840845e0ee5SBram Moolenaar  call setline(h + 1, repeat('x', winwidth(0) - 1))
1841845e0ee5SBram Moolenaar  call feedkeys("GAx", 'xt')
1842845e0ee5SBram Moolenaar  redraw!
1843845e0ee5SBram Moolenaar  call assert_equal(h - 1, winline())
1844845e0ee5SBram Moolenaar  call assert_equal(3, line('w0'))
1845845e0ee5SBram Moolenaar
1846845e0ee5SBram Moolenaar  close!
1847845e0ee5SBram Moolenaarendfunc
1848845e0ee5SBram Moolenaar
184921cbe175SBram Moolenaarfunc Test_edit_browse()
185021cbe175SBram Moolenaar  " in the GUI this opens a file picker, we only test the terminal behavior
185121cbe175SBram Moolenaar  CheckNotGui
185221cbe175SBram Moolenaar
185321cbe175SBram Moolenaar  " ":browse xxx" checks for the FileExplorer augroup and assumes editing "."
185421cbe175SBram Moolenaar  " works then.
185521cbe175SBram Moolenaar  augroup FileExplorer
185621cbe175SBram Moolenaar    au!
185721cbe175SBram Moolenaar  augroup END
185821cbe175SBram Moolenaar
185921cbe175SBram Moolenaar  " When the USE_FNAME_CASE is defined this used to cause a crash.
186021cbe175SBram Moolenaar  browse enew
186121cbe175SBram Moolenaar  bwipe!
186221cbe175SBram Moolenaar
186321cbe175SBram Moolenaar  browse split
186421cbe175SBram Moolenaar  bwipe!
186521cbe175SBram Moolenaarendfunc
186621cbe175SBram Moolenaar
1867caf73dcfSBram Moolenaarfunc Test_read_invalid()
1868caf73dcfSBram Moolenaar  set encoding=latin1
1869caf73dcfSBram Moolenaar  " This was not properly checking for going past the end.
1870caf73dcfSBram Moolenaar  call assert_fails('r`=', 'E484')
1871caf73dcfSBram Moolenaar  set encoding=utf-8
1872caf73dcfSBram Moolenaarendfunc
1873caf73dcfSBram Moolenaar
187459585497SYegappan Lakshmanan" Test for the 'revins' option
187559585497SYegappan Lakshmananfunc Test_edit_revins()
187659585497SYegappan Lakshmanan  CheckFeature rightleft
187759585497SYegappan Lakshmanan  new
187859585497SYegappan Lakshmanan  set revins
187959585497SYegappan Lakshmanan  exe "normal! ione\ttwo three"
188059585497SYegappan Lakshmanan  call assert_equal("eerht owt\teno", getline(1))
188159585497SYegappan Lakshmanan  call setline(1, "one\ttwo three")
188259585497SYegappan Lakshmanan  normal! gg$bi a
188359585497SYegappan Lakshmanan  call assert_equal("one\ttwo a three", getline(1))
188459585497SYegappan Lakshmanan  exe "normal! $bi\<BS>\<BS>"
188559585497SYegappan Lakshmanan  call assert_equal("one\ttwo a ree", getline(1))
188659585497SYegappan Lakshmanan  exe "normal! 0wi\<C-W>"
188759585497SYegappan Lakshmanan  call assert_equal("one\t a ree", getline(1))
188859585497SYegappan Lakshmanan  exe "normal! 0wi\<C-U>"
188959585497SYegappan Lakshmanan  call assert_equal("one\t ", getline(1))
189059585497SYegappan Lakshmanan  " newline in insert mode starts at the end of the line
189159585497SYegappan Lakshmanan  call setline(1, 'one two three')
189259585497SYegappan Lakshmanan  exe "normal! wi\nfour"
189359585497SYegappan Lakshmanan  call assert_equal(['one two three', 'ruof'], getline(1, '$'))
189459585497SYegappan Lakshmanan  set revins&
189559585497SYegappan Lakshmanan  bw!
189659585497SYegappan Lakshmananendfunc
189759585497SYegappan Lakshmanan
1898*35a9a00aSBram Moolenaar" Test for getting the character of the line below after "p"
1899*35a9a00aSBram Moolenaarfunc Test_edit_put_CTRL_E()
1900*35a9a00aSBram Moolenaar  set encoding=latin1
1901*35a9a00aSBram Moolenaar  new
1902*35a9a00aSBram Moolenaar  let @" = ''
1903*35a9a00aSBram Moolenaar  sil! norm orggRx
1904*35a9a00aSBram Moolenaar  sil! norm pr
1905*35a9a00aSBram Moolenaar  call assert_equal(['r', 'r'], getline(1, 2))
1906*35a9a00aSBram Moolenaar  bwipe!
1907*35a9a00aSBram Moolenaar  set encoding=utf-8
1908*35a9a00aSBram Moolenaarendfunc
1909*35a9a00aSBram Moolenaar
1910bc2b71d4SBram Moolenaar" vim: shiftwidth=2 sts=2 expandtab
1911