xref: /vim-8.2.3635/src/testdir/test_edit.vim (revision 9faec4e3)
1" Test for edit functions
2
3if exists("+t_kD")
4  let &t_kD="[3;*~"
5endif
6
7source check.vim
8
9" Needed for testing basic rightleft: Test_edit_rightleft
10source view_util.vim
11
12" Needs to come first until the bug in getchar() is
13" fixed: https://groups.google.com/d/msg/vim_dev/fXL9yme4H4c/bOR-U6_bAQAJ
14func Test_edit_00b()
15  new
16  call setline(1, ['abc '])
17  inoreabbr <buffer> h here some more
18  call cursor(1, 4)
19  " <c-l> expands the abbreviation and ends insertmode
20  call feedkeys(":set im\<cr> h\<c-l>:set noim\<cr>", 'tix')
21  call assert_equal(['abc here some more '], getline(1,'$'))
22  iunabbr <buffer> h
23  bw!
24endfunc
25
26func Test_edit_01()
27  " set for Travis CI?
28  "  set nocp noesckeys
29  new
30  " 1) empty buffer
31  call assert_equal([''], getline(1,'$'))
32  " 2) delete in an empty line
33  call feedkeys("i\<del>\<esc>", 'tnix')
34  call assert_equal([''], getline(1,'$'))
35  %d
36  " 3) delete one character
37  call setline(1, 'a')
38  call feedkeys("i\<del>\<esc>", 'tnix')
39  call assert_equal([''], getline(1,'$'))
40  %d
41  " 4) delete a multibyte character
42  call setline(1, "\u0401")
43  call feedkeys("i\<del>\<esc>", 'tnix')
44  call assert_equal([''], getline(1,'$'))
45  %d
46  " 5.1) delete linebreak with 'bs' option containing eol
47  let _bs=&bs
48  set bs=eol
49  call setline(1, ["abc def", "ghi jkl"])
50  call cursor(1, 1)
51  call feedkeys("A\<del>\<esc>", 'tnix')
52  call assert_equal(['abc defghi jkl'], getline(1, 2))
53  %d
54  " 5.2) delete linebreak with backspace option w/out eol
55  set bs=
56  call setline(1, ["abc def", "ghi jkl"])
57  call cursor(1, 1)
58  call feedkeys("A\<del>\<esc>", 'tnix')
59  call assert_equal(["abc def", "ghi jkl"], getline(1, 2))
60  let &bs=_bs
61  bw!
62endfunc
63
64func Test_edit_02()
65  " Change cursor position in InsertCharPre command
66  new
67  call setline(1, 'abc')
68  call cursor(1, 1)
69  fu! DoIt(...)
70    call cursor(1, 4)
71    if len(a:000)
72      let v:char=a:1
73    endif
74  endfu
75  au InsertCharPre <buffer> :call DoIt('y')
76  call feedkeys("ix\<esc>", 'tnix')
77  call assert_equal(['abcy'], getline(1, '$'))
78  " Setting <Enter> in InsertCharPre
79  au! InsertCharPre <buffer> :call DoIt("\n")
80  call setline(1, 'abc')
81  call cursor(1, 1)
82  call feedkeys("ix\<esc>", 'tnix')
83  call assert_equal(['abc', ''], getline(1, '$'))
84  %d
85  au! InsertCharPre
86  " Change cursor position in InsertEnter command
87  " 1) when setting v:char, keeps changed cursor position
88  au! InsertEnter <buffer> :call DoIt('y')
89  call setline(1, 'abc')
90  call cursor(1, 1)
91  call feedkeys("ix\<esc>", 'tnix')
92  call assert_equal(['abxc'], getline(1, '$'))
93  " 2) when not setting v:char, restores changed cursor position
94  au! InsertEnter <buffer> :call DoIt()
95  call setline(1, 'abc')
96  call cursor(1, 1)
97  call feedkeys("ix\<esc>", 'tnix')
98  call assert_equal(['xabc'], getline(1, '$'))
99  au! InsertEnter
100  delfu DoIt
101  bw!
102endfunc
103
104func Test_edit_03()
105  " Change cursor after <c-o> command to end of line
106  new
107  call setline(1, 'abc')
108  call cursor(1, 1)
109  call feedkeys("i\<c-o>$y\<esc>", 'tnix')
110  call assert_equal(['abcy'], getline(1, '$'))
111  %d
112  call setline(1, 'abc')
113  call cursor(1, 1)
114  call feedkeys("i\<c-o>80|y\<esc>", 'tnix')
115  call assert_equal(['abcy'], getline(1, '$'))
116  %d
117  call setline(1, 'abc')
118  call feedkeys("Ad\<c-o>:s/$/efg/\<cr>hij", 'tnix')
119  call assert_equal(['hijabcdefg'], getline(1, '$'))
120  bw!
121endfunc
122
123func Test_edit_04()
124  " test for :stopinsert
125  new
126  call setline(1, 'abc')
127  call cursor(1, 1)
128  call feedkeys("i\<c-o>:stopinsert\<cr>$", 'tnix')
129  call feedkeys("aX\<esc>", 'tnix')
130  call assert_equal(['abcX'], getline(1, '$'))
131  %d
132  bw!
133endfunc
134
135func Test_edit_05()
136  " test for folds being opened
137  new
138  call setline(1, ['abcX', 'abcX', 'zzzZ'])
139  call cursor(1, 1)
140  set foldmethod=manual foldopen+=insert
141  " create fold for those two lines
142  norm! Vjzf
143  call feedkeys("$ay\<esc>", 'tnix')
144  call assert_equal(['abcXy', 'abcX', 'zzzZ'], getline(1, '$'))
145  %d
146  call setline(1, ['abcX', 'abcX', 'zzzZ'])
147  call cursor(1, 1)
148  set foldmethod=manual foldopen-=insert
149  " create fold for those two lines
150  norm! Vjzf
151  call feedkeys("$ay\<esc>", 'tnix')
152  call assert_equal(['abcXy', 'abcX', 'zzzZ'], getline(1, '$'))
153  %d
154  bw!
155endfunc
156
157func Test_edit_06()
158  " Test in diff mode
159  CheckFeature diff
160  CheckExecutable diff
161  new
162  call setline(1, ['abc', 'xxx', 'yyy'])
163  vnew
164  call setline(1, ['abc', 'zzz', 'xxx', 'yyy'])
165  wincmd p
166  diffthis
167  wincmd p
168  diffthis
169  wincmd p
170  call cursor(2, 1)
171  norm! zt
172  call feedkeys("Ozzz\<esc>", 'tnix')
173  call assert_equal(['abc', 'zzz', 'xxx', 'yyy'], getline(1,'$'))
174  bw!
175  bw!
176endfunc
177
178func Test_edit_07()
179  " 1) Test with completion <c-l> when popupmenu is visible
180  new
181  call setline(1, 'J')
182
183  func! ListMonths()
184    call complete(col('.')-1, ['January', 'February', 'March',
185    \ 'April', 'May', 'June', 'July', 'August', 'September',
186    \ 'October', 'November', 'December'])
187    return ''
188  endfunc
189  inoremap <buffer> <F5> <C-R>=ListMonths()<CR>
190
191  call feedkeys("A\<f5>\<c-p>". repeat("\<down>", 6)."\<c-l>\<down>\<c-l>\<cr>", 'tx')
192  call assert_equal(['July'], getline(1,'$'))
193  " 1) Test completion when InsertCharPre kicks in
194  %d
195  call setline(1, 'J')
196  fu! DoIt()
197    if v:char=='u'
198      let v:char='an'
199    endif
200  endfu
201  au InsertCharPre <buffer> :call DoIt()
202  call feedkeys("A\<f5>\<c-p>u\<cr>\<c-l>\<cr>", 'tx')
203  call assert_equal(["Jan\<c-l>",''], 1->getline('$'))
204  %d
205  call setline(1, 'J')
206  call feedkeys("A\<f5>\<c-p>u\<down>\<c-l>\<cr>", 'tx')
207  call assert_equal(["January"], 1->getline('$'))
208
209  delfu ListMonths
210  delfu DoIt
211  iunmap <buffer> <f5>
212  bw!
213endfunc
214
215func Test_edit_08()
216  " reset insertmode from i_ctrl-r_=
217  let g:bufnr = bufnr('%')
218  new
219  call setline(1, ['abc'])
220  call cursor(1, 4)
221  call feedkeys(":set im\<cr>ZZZ\<c-r>=setbufvar(g:bufnr,'&im', 0)\<cr>",'tnix')
222  call assert_equal(['abZZZc'], getline(1,'$'))
223  call assert_equal([0, 1, 1, 0], getpos('.'))
224  call assert_false(0, '&im')
225  bw!
226  unlet g:bufnr
227endfunc
228
229func Test_edit_09()
230  " test i_CTRL-\ combinations
231  new
232  call setline(1, ['abc', 'def', 'ghi'])
233  call cursor(1, 1)
234  " 1) CTRL-\ CTLR-N
235  call feedkeys(":set im\<cr>\<c-\>\<c-n>ccABC\<c-l>", 'txin')
236  call assert_equal(['ABC', 'def', 'ghi'], getline(1,'$'))
237  call setline(1, ['ABC', 'def', 'ghi'])
238  " 2) CTRL-\ CTLR-G
239  call feedkeys("j0\<c-\>\<c-g>ZZZ\<cr>\<c-l>", 'txin')
240  call assert_equal(['ABC', 'ZZZ', 'def', 'ghi'], getline(1,'$'))
241  call feedkeys("I\<c-\>\<c-g>YYY\<c-l>", 'txin')
242  call assert_equal(['ABC', 'ZZZ', 'YYYdef', 'ghi'], getline(1,'$'))
243  set noinsertmode
244  " 3) CTRL-\ CTRL-O
245  call setline(1, ['ABC', 'ZZZ', 'def', 'ghi'])
246  call cursor(1, 1)
247  call feedkeys("A\<c-o>ix", 'txin')
248  call assert_equal(['ABxC', 'ZZZ', 'def', 'ghi'], getline(1,'$'))
249  call feedkeys("A\<c-\>\<c-o>ix", 'txin')
250  call assert_equal(['ABxCx', 'ZZZ', 'def', 'ghi'], getline(1,'$'))
251  " 4) CTRL-\ a (should be inserted literally, not special after <c-\>
252  call setline(1, ['ABC', 'ZZZ', 'def', 'ghi'])
253  call cursor(1, 1)
254  call feedkeys("A\<c-\>a", 'txin')
255  call assert_equal(["ABC\<c-\>a", 'ZZZ', 'def', 'ghi'], getline(1, '$'))
256  bw!
257endfunc
258
259func Test_edit_11()
260  " Test that indenting kicks in
261  new
262  set cindent
263  call setline(1, ['{', '', ''])
264  call cursor(2, 1)
265  call feedkeys("i\<c-f>int c;\<esc>", 'tnix')
266  call cursor(3, 1)
267  call feedkeys("\<Insert>/* comment */", 'tnix')
268  call assert_equal(['{', "\<tab>int c;", "/* comment */"], getline(1, '$'))
269  " added changed cindentkeys slightly
270  set cindent cinkeys+=*/
271  call setline(1, ['{', '', ''])
272  call cursor(2, 1)
273  call feedkeys("i\<c-f>int c;\<esc>", 'tnix')
274  call cursor(3, 1)
275  call feedkeys("i/* comment */", 'tnix')
276  call assert_equal(['{', "\<tab>int c;", "\<tab>/* comment */"], getline(1, '$'))
277  set cindent cinkeys+==end
278  call feedkeys("oend\<cr>\<esc>", 'tnix')
279  call assert_equal(['{', "\<tab>int c;", "\<tab>/* comment */", "\tend", ''], getline(1, '$'))
280  set cinkeys-==end
281  %d
282  " Use indentexpr instead of cindenting
283  func! Do_Indent()
284    if v:lnum == 3
285      return 3*shiftwidth()
286    else
287      return 2*shiftwidth()
288    endif
289  endfunc
290  setl indentexpr=Do_Indent() indentkeys+=*/
291  call setline(1, ['{', '', ''])
292  call cursor(2, 1)
293  call feedkeys("i\<c-f>int c;\<esc>", 'tnix')
294  call cursor(3, 1)
295  call feedkeys("i/* comment */", 'tnix')
296  call assert_equal(['{', "\<tab>\<tab>int c;", "\<tab>\<tab>\<tab>/* comment */"], getline(1, '$'))
297  set cinkeys&vim indentkeys&vim
298  set nocindent indentexpr=
299  delfu Do_Indent
300  bw!
301endfunc
302
303func Test_edit_11_indentexpr()
304  " Test that indenting kicks in
305  new
306  " Use indentexpr instead of cindenting
307  func! Do_Indent()
308    let pline=prevnonblank(v:lnum)
309    if empty(getline(v:lnum))
310      if getline(pline) =~ 'if\|then'
311        return shiftwidth()
312      else
313        return 0
314      endif
315    else
316        return 0
317    endif
318  endfunc
319  setl indentexpr=Do_Indent() indentkeys+=0=then,0=fi
320  call setline(1, ['if [ $this ]'])
321  call cursor(1, 1)
322  call feedkeys("othen\<cr>that\<cr>fi", 'tnix')
323  call assert_equal(['if [ $this ]', "then", "\<tab>that", "fi"], getline(1, '$'))
324  set cinkeys&vim indentkeys&vim
325  set nocindent indentexpr=
326  delfu Do_Indent
327  bw!
328endfunc
329
330" Test changing indent in replace mode
331func Test_edit_12()
332  new
333  call setline(1, ["\tabc", "\tdef"])
334  call cursor(2, 4)
335  call feedkeys("R^\<c-d>", 'tnix')
336  call assert_equal(["\tabc", "def"], getline(1, '$'))
337  call assert_equal([0, 2, 2, 0], '.'->getpos())
338  %d
339  call setline(1, ["\tabc", "\t\tdef"])
340  call cursor(2, 2)
341  call feedkeys("R^\<c-d>", 'tnix')
342  call assert_equal(["\tabc", "def"], getline(1, '$'))
343  call assert_equal([0, 2, 1, 0], getpos('.'))
344  %d
345  call setline(1, ["\tabc", "\t\tdef"])
346  call cursor(2, 2)
347  call feedkeys("R\<c-t>", 'tnix')
348  call assert_equal(["\tabc", "\t\t\tdef"], getline(1, '$'))
349  call assert_equal([0, 2, 2, 0], getpos('.'))
350  bw!
351  10vnew
352  call setline(1, ["\tabc", "\t\tdef"])
353  call cursor(2, 2)
354  call feedkeys("R\<c-t>", 'tnix')
355  call assert_equal(["\tabc", "\t\t\tdef"], getline(1, '$'))
356  call assert_equal([0, 2, 2, 0], getpos('.'))
357  %d
358  set sw=4
359  call setline(1, ["\tabc", "\t\tdef"])
360  call cursor(2, 2)
361  call feedkeys("R\<c-t>\<c-t>", 'tnix')
362  call assert_equal(["\tabc", "\t\t\tdef"], getline(1, '$'))
363  call assert_equal([0, 2, 2, 0], getpos('.'))
364  %d
365  call setline(1, ["\tabc", "\t\tdef"])
366  call cursor(2, 2)
367  call feedkeys("R\<c-t>\<c-t>", 'tnix')
368  call assert_equal(["\tabc", "\t\t\tdef"], getline(1, '$'))
369  call assert_equal([0, 2, 2, 0], getpos('.'))
370  set sw&
371
372  " In replace mode, after hitting enter in a line with tab characters,
373  " pressing backspace should restore the tab characters.
374  %d
375  setlocal autoindent backspace=2
376  call setline(1, "\tone\t\ttwo")
377  exe "normal ggRred\<CR>six" .. repeat("\<BS>", 8)
378  call assert_equal(["\tone\t\ttwo"], getline(1, '$'))
379  bw!
380endfunc
381
382func Test_edit_13()
383  " Test smartindenting
384  if exists("+smartindent")
385    new
386    set smartindent autoindent
387    call setline(1, ["\tabc"])
388    call feedkeys("A {\<cr>more\<cr>}\<esc>", 'tnix')
389    call assert_equal(["\tabc {", "\t\tmore", "\t}"], getline(1, '$'))
390    set smartindent& autoindent&
391    bwipe!
392  endif
393
394  " Test autoindent removing indent of blank line.
395  new
396  call setline(1, '    foo bar baz')
397  set autoindent
398  exe "normal 0eea\<CR>\<CR>\<Esc>"
399  call assert_equal("    foo bar", getline(1))
400  call assert_equal("", getline(2))
401  call assert_equal("    baz", getline(3))
402  set autoindent&
403
404  " pressing <C-U> to erase line should keep the indent with 'autoindent'
405  set backspace=2 autoindent
406  %d
407  exe "normal i\tone\<CR>three\<C-U>two"
408  call assert_equal(["\tone", "\ttwo"], getline(1, '$'))
409  set backspace& autoindent&
410
411  bwipe!
412endfunc
413
414func Test_edit_CR()
415  " Test for <CR> in insert mode
416  " basically only in quickfix mode ist tested, the rest
417  " has been taken care of by other tests
418  CheckFeature quickfix
419  botright new
420  call writefile(range(1, 10), 'Xqflist.txt')
421  call setqflist([{'filename': 'Xqflist.txt', 'lnum': 2}])
422  copen
423  set modifiable
424  call feedkeys("A\<cr>", 'tnix')
425  call assert_equal('Xqflist.txt', bufname(''))
426  call assert_equal(2, line('.'))
427  cclose
428  botright new
429  call setloclist(0, [{'filename': 'Xqflist.txt', 'lnum': 10}])
430  lopen
431  set modifiable
432  call feedkeys("A\<cr>", 'tnix')
433  call assert_equal('Xqflist.txt', bufname(''))
434  call assert_equal(10, line('.'))
435  call feedkeys("A\<Enter>", 'tnix')
436  call feedkeys("A\<kEnter>", 'tnix')
437  call feedkeys("A\n", 'tnix')
438  call feedkeys("A\r", 'tnix')
439  call assert_equal(map(range(1, 10), 'string(v:val)') + ['', '', '', ''], getline(1, '$'))
440  bw!
441  lclose
442  call delete('Xqflist.txt')
443endfunc
444
445func Test_edit_CTRL_()
446  CheckFeature rightleft
447  " disabled for Windows builds, why?
448  CheckNotMSWindows
449  let _encoding=&encoding
450  set encoding=utf-8
451  " Test for CTRL-_
452  new
453  call setline(1, ['abc'])
454  call cursor(1, 1)
455  call feedkeys("i\<c-_>xyz\<esc>", 'tnix')
456  call assert_equal(["\<C-_>xyzabc"], getline(1, '$'))
457  call assert_false(&revins)
458  set ari
459  call setline(1, ['abc'])
460  call cursor(1, 1)
461  call feedkeys("i\<c-_>xyz\<esc>", 'tnix')
462  call assert_equal(["æèñabc"], getline(1, '$'))
463  call assert_true(&revins)
464  call setline(1, ['abc'])
465  call cursor(1, 1)
466  call feedkeys("i\<c-_>xyz\<esc>", 'tnix')
467  call assert_equal(["xyzabc"], getline(1, '$'))
468  call assert_false(&revins)
469  set noari
470  let &encoding=_encoding
471  bw!
472endfunc
473
474" needs to come first, to have the @. register empty
475func Test_edit_00a_CTRL_A()
476  " Test pressing CTRL-A
477  new
478  call setline(1, repeat([''], 5))
479  call cursor(1, 1)
480  try
481    call feedkeys("A\<NUL>", 'tnix')
482  catch /^Vim\%((\a\+)\)\=:E29/
483    call assert_true(1, 'E29 error caught')
484  endtry
485  call cursor(1, 1)
486  call feedkeys("Afoobar \<esc>", 'tnix')
487  call cursor(2, 1)
488  call feedkeys("A\<c-a>more\<esc>", 'tnix')
489  call cursor(3, 1)
490  call feedkeys("A\<NUL>and more\<esc>", 'tnix')
491  call assert_equal(['foobar ', 'foobar more', 'foobar morend more', '', ''], getline(1, '$'))
492  bw!
493endfunc
494
495func Test_edit_CTRL_EY()
496  " Ctrl-E/ Ctrl-Y in insert mode completion to scroll
497  10new
498  call setline(1, range(1, 100))
499  call cursor(30, 1)
500  norm! z.
501  call feedkeys("A\<c-x>\<c-e>\<c-e>\<c-e>\<c-e>\<c-e>", 'tnix')
502  call assert_equal(30, winsaveview()['topline'])
503  call assert_equal([0, 30, 2, 0], getpos('.'))
504  call feedkeys("A\<c-x>\<c-e>\<c-e>\<c-e>\<c-e>\<c-e>", 'tnix')
505  call feedkeys("A\<c-x>".repeat("\<c-y>", 10), 'tnix')
506  call assert_equal(21, winsaveview()['topline'])
507  call assert_equal([0, 30, 2, 0], getpos('.'))
508  bw!
509endfunc
510
511func Test_edit_CTRL_G()
512  new
513  call setline(1, ['foobar', 'foobar', 'foobar'])
514  call cursor(2, 4)
515  call feedkeys("ioooooooo\<c-g>k\<c-r>.\<esc>", 'tnix')
516  call assert_equal(['foooooooooobar', 'foooooooooobar', 'foobar'], getline(1, '$'))
517  call assert_equal([0, 1, 11, 0], getpos('.'))
518  call feedkeys("i\<c-g>k\<esc>", 'tnix')
519  call assert_equal([0, 1, 10, 0], getpos('.'))
520  call cursor(2, 4)
521  call feedkeys("i\<c-g>jzzzz\<esc>", 'tnix')
522  call assert_equal(['foooooooooobar', 'foooooooooobar', 'foozzzzbar'], getline(1, '$'))
523  call assert_equal([0, 3, 7, 0], getpos('.'))
524  call feedkeys("i\<c-g>j\<esc>", 'tnix')
525  call assert_equal([0, 3, 6, 0], getpos('.'))
526  bw!
527endfunc
528
529func Test_edit_CTRL_I()
530  " Tab in completion mode
531  let path=expand("%:p:h")
532  new
533  call setline(1, [path. "/", ''])
534  call feedkeys("Arunt\<c-x>\<c-f>\<tab>\<cr>\<esc>", 'tnix')
535  call assert_match('runtest\.vim', getline(1))
536  %d
537  call writefile(['one', 'two', 'three'], 'Xinclude.txt')
538  let include='#include Xinclude.txt'
539  call setline(1, [include, ''])
540  call cursor(2, 1)
541  call feedkeys("A\<c-x>\<tab>\<cr>\<esc>", 'tnix')
542  call assert_equal([include, 'one', ''], getline(1, '$'))
543  call feedkeys("2ggC\<c-x>\<tab>\<down>\<cr>\<esc>", 'tnix')
544  call assert_equal([include, 'two', ''], getline(1, '$'))
545  call feedkeys("2ggC\<c-x>\<tab>\<down>\<down>\<cr>\<esc>", 'tnix')
546  call assert_equal([include, 'three', ''], getline(1, '$'))
547  call feedkeys("2ggC\<c-x>\<tab>\<down>\<down>\<down>\<cr>\<esc>", 'tnix')
548  call assert_equal([include, '', ''], getline(1, '$'))
549  call delete("Xinclude.txt")
550  bw!
551endfunc
552
553func Test_edit_CTRL_K()
554  " Test pressing CTRL-K (basically only dictionary completion and digraphs
555  " the rest is already covered
556  call writefile(['A', 'AA', 'AAA', 'AAAA'], 'Xdictionary.txt')
557  set dictionary=Xdictionary.txt
558  new
559  call setline(1, 'A')
560  call cursor(1, 1)
561  call feedkeys("A\<c-x>\<c-k>\<cr>\<esc>", 'tnix')
562  call assert_equal(['AA', ''], getline(1, '$'))
563  %d
564  call setline(1, 'A')
565  call cursor(1, 1)
566  call feedkeys("A\<c-x>\<c-k>\<down>\<cr>\<esc>", 'tnix')
567  call assert_equal(['AAA'], getline(1, '$'))
568  %d
569  call setline(1, 'A')
570  call cursor(1, 1)
571  call feedkeys("A\<c-x>\<c-k>\<down>\<down>\<cr>\<esc>", 'tnix')
572  call assert_equal(['AAAA'], getline(1, '$'))
573  %d
574  call setline(1, 'A')
575  call cursor(1, 1)
576  call feedkeys("A\<c-x>\<c-k>\<down>\<down>\<down>\<cr>\<esc>", 'tnix')
577  call assert_equal(['A'], getline(1, '$'))
578  %d
579  call setline(1, 'A')
580  call cursor(1, 1)
581  call feedkeys("A\<c-x>\<c-k>\<down>\<down>\<down>\<down>\<cr>\<esc>", 'tnix')
582  call assert_equal(['AA'], getline(1, '$'))
583
584  " press an unexpected key after dictionary completion
585  %d
586  call setline(1, 'A')
587  call cursor(1, 1)
588  call feedkeys("A\<c-x>\<c-k>\<c-]>\<cr>\<esc>", 'tnix')
589  call assert_equal(['AA', ''], getline(1, '$'))
590  %d
591  call setline(1, 'A')
592  call cursor(1, 1)
593  call feedkeys("A\<c-x>\<c-k>\<c-s>\<cr>\<esc>", 'tnix')
594  call assert_equal(["AA\<c-s>", ''], getline(1, '$'))
595  %d
596  call setline(1, 'A')
597  call cursor(1, 1)
598  call feedkeys("A\<c-x>\<c-k>\<c-f>\<cr>\<esc>", 'tnix')
599  call assert_equal(["AA\<c-f>", ''], getline(1, '$'))
600
601  set dictionary=
602  %d
603  call setline(1, 'A')
604  call cursor(1, 1)
605  let v:testing = 1
606  try
607    call feedkeys("A\<c-x>\<c-k>\<esc>", 'tnix')
608  catch
609    " error sleeps 2 seconds, when v:testing is not set
610    let v:testing = 0
611  endtry
612  call delete('Xdictionary.txt')
613
614  call test_override("char_avail", 1)
615  set showcmd
616  %d
617  call feedkeys("A\<c-k>a:\<esc>", 'tnix')
618  call assert_equal(['ä'], getline(1, '$'))
619  call test_override("char_avail", 0)
620  set noshowcmd
621
622  bw!
623endfunc
624
625func Test_edit_CTRL_L()
626  " Test Ctrl-X Ctrl-L (line completion)
627  new
628  set complete=.
629  call setline(1, ['one', 'two', 'three', '', '', '', ''])
630  call cursor(4, 1)
631  call feedkeys("A\<c-x>\<c-l>\<esc>", 'tnix')
632  call assert_equal(['one', 'two', 'three', 'three', '', '', ''], getline(1, '$'))
633  call feedkeys("cct\<c-x>\<c-l>\<c-n>\<esc>", 'tnix')
634  call assert_equal(['one', 'two', 'three', 't', '', '', ''], getline(1, '$'))
635  call feedkeys("cct\<c-x>\<c-l>\<c-n>\<c-n>\<esc>", 'tnix')
636  call assert_equal(['one', 'two', 'three', 'two', '', '', ''], getline(1, '$'))
637  call feedkeys("cct\<c-x>\<c-l>\<c-n>\<c-n>\<c-n>\<esc>", 'tnix')
638  call assert_equal(['one', 'two', 'three', 'three', '', '', ''], getline(1, '$'))
639  call feedkeys("cct\<c-x>\<c-l>\<c-n>\<c-n>\<c-n>\<c-n>\<esc>", 'tnix')
640  call assert_equal(['one', 'two', 'three', 't', '', '', ''], getline(1, '$'))
641  call feedkeys("cct\<c-x>\<c-l>\<c-p>\<esc>", 'tnix')
642  call assert_equal(['one', 'two', 'three', 'two', '', '', ''], getline(1, '$'))
643  call feedkeys("cct\<c-x>\<c-l>\<c-p>\<c-p>\<esc>", 'tnix')
644  call assert_equal(['one', 'two', 'three', 't', '', '', ''], getline(1, '$'))
645  call feedkeys("cct\<c-x>\<c-l>\<c-p>\<c-p>\<c-p>\<esc>", 'tnix')
646  call assert_equal(['one', 'two', 'three', 'three', '', '', ''], getline(1, '$'))
647  set complete=
648  call cursor(5, 1)
649  call feedkeys("A\<c-x>\<c-l>\<c-p>\<c-n>\<esc>", 'tnix')
650  call assert_equal(['one', 'two', 'three', 'three', "\<c-l>\<c-p>\<c-n>", '', ''], getline(1, '$'))
651  set complete&
652  %d
653  if has("conceal") && has("syntax")
654    call setline(1, ['foo', 'bar', 'foobar'])
655    call test_override("char_avail", 1)
656    set conceallevel=2 concealcursor=n
657    syn on
658    syn match ErrorMsg "^bar"
659    call matchadd("Conceal", 'oo', 10, -1, {'conceal': 'X'})
660    func! DoIt()
661      let g:change=1
662    endfunc
663    au! TextChangedI <buffer> :call DoIt()
664
665    call cursor(2, 1)
666    call assert_false(exists("g:change"))
667    call feedkeys("A \<esc>", 'tnix')
668    call assert_equal(['foo', 'bar ', 'foobar'], getline(1, '$'))
669    call assert_equal(1, g:change)
670
671    call test_override("char_avail", 0)
672    call clearmatches()
673    syn off
674    au! TextChangedI
675    delfu DoIt
676    unlet! g:change
677  endif
678  bw!
679endfunc
680
681func Test_edit_CTRL_N()
682  " Check keyword completion
683  for e in ['latin1', 'utf-8']
684    exe 'set encoding=' .. e
685    new
686    set complete=.
687    call setline(1, ['INFER', 'loWER', '', '', ])
688    call cursor(3, 1)
689    call feedkeys("Ai\<c-n>\<cr>\<esc>", "tnix")
690    call feedkeys("ILO\<c-n>\<cr>\<esc>", 'tnix')
691    call assert_equal(['INFER', 'loWER', 'i', 'LO', '', ''], getline(1, '$'), e)
692    %d
693    call setline(1, ['INFER', 'loWER', '', '', ])
694    call cursor(3, 1)
695    set ignorecase infercase
696    call feedkeys("Ii\<c-n>\<cr>\<esc>", "tnix")
697    call feedkeys("ILO\<c-n>\<cr>\<esc>", 'tnix')
698    call assert_equal(['INFER', 'loWER', 'infer', 'LOWER', '', ''], getline(1, '$'), e)
699
700    set noignorecase noinfercase complete&
701    bw!
702  endfor
703endfunc
704
705func Test_edit_CTRL_O()
706  " Check for CTRL-O in insert mode
707  new
708  inoreabbr <buffer> h here some more
709  call setline(1, ['abc', 'def'])
710  call cursor(1, 1)
711  " Ctrl-O after an abbreviation
712  exe "norm A h\<c-o>:set nu\<cr> text"
713  call assert_equal(['abc here some more text', 'def'], getline(1, '$'))
714  call assert_true(&nu)
715  set nonu
716  iunabbr <buffer> h
717  " Ctrl-O at end of line with 've'=onemore
718  call cursor(1, 1)
719  call feedkeys("A\<c-o>:let g:a=getpos('.')\<cr>\<esc>", 'tnix')
720  call assert_equal([0, 1, 23, 0], g:a)
721  call cursor(1, 1)
722  set ve=onemore
723  call feedkeys("A\<c-o>:let g:a=getpos('.')\<cr>\<esc>", 'tnix')
724  call assert_equal([0, 1, 24, 0], g:a)
725  set ve=
726  unlet! g:a
727  bw!
728endfunc
729
730func Test_edit_CTRL_R()
731  " Insert Register
732  new
733  call test_override("ALL", 1)
734  set showcmd
735  call feedkeys("AFOOBAR eins zwei\<esc>", 'tnix')
736  call feedkeys("O\<c-r>.", 'tnix')
737  call feedkeys("O\<c-r>=10*500\<cr>\<esc>", 'tnix')
738  call feedkeys("O\<c-r>=getreg('=', 1)\<cr>\<esc>", 'tnix')
739  call assert_equal(["getreg('=', 1)", '5000', "FOOBAR eins zwei", "FOOBAR eins zwei"], getline(1, '$'))
740  call test_override("ALL", 0)
741  set noshowcmd
742  bw!
743endfunc
744
745func Test_edit_CTRL_S()
746  " Test pressing CTRL-S (basically only spellfile completion)
747  " the rest is already covered
748  new
749  if !has("spell")
750    call setline(1, 'vim')
751    call feedkeys("A\<c-x>ss\<cr>\<esc>", 'tnix')
752    call assert_equal(['vims', ''], getline(1, '$'))
753    bw!
754    return
755  endif
756  call setline(1, 'vim')
757  " spell option not yet set
758  try
759    call feedkeys("A\<c-x>\<c-s>\<cr>\<esc>", 'tnix')
760  catch /^Vim\%((\a\+)\)\=:E756/
761    call assert_true(1, 'error caught')
762  endtry
763  call assert_equal(['vim', ''], getline(1, '$'))
764  %d
765  setl spell spelllang=en
766  call setline(1, 'vim')
767  call cursor(1, 1)
768  call feedkeys("A\<c-x>\<c-s>\<cr>\<esc>", 'tnix')
769  call assert_equal(['Vim', ''], getline(1, '$'))
770  %d
771  call setline(1, 'vim')
772  call cursor(1, 1)
773  call feedkeys("A\<c-x>\<c-s>\<down>\<cr>\<esc>", 'tnix')
774  call assert_equal(['Aim'], getline(1, '$'))
775  %d
776  call setline(1, 'vim')
777  call cursor(1, 1)
778  call feedkeys("A\<c-x>\<c-s>\<c-p>\<cr>\<esc>", 'tnix')
779  call assert_equal(['vim', ''], getline(1, '$'))
780  %d
781  " empty buffer
782  call cursor(1, 1)
783  call feedkeys("A\<c-x>\<c-s>\<c-p>\<cr>\<esc>", 'tnix')
784  call assert_equal(['', ''], getline(1, '$'))
785  setl nospell
786  bw!
787endfunc
788
789func Test_edit_CTRL_T()
790  " Check for CTRL-T and CTRL-X CTRL-T in insert mode
791  " 1) increase indent
792  new
793  call setline(1, "abc")
794  call cursor(1, 1)
795  call feedkeys("A\<c-t>xyz", 'tnix')
796  call assert_equal(["\<tab>abcxyz"], getline(1, '$'))
797  " 2) also when paste option is set
798  set paste
799  call setline(1, "abc")
800  call cursor(1, 1)
801  call feedkeys("A\<c-t>xyz", 'tnix')
802  call assert_equal(["\<tab>abcxyz"], getline(1, '$'))
803  set nopaste
804  " CTRL-X CTRL-T (thesaurus complete)
805  call writefile(['angry furious mad enraged'], 'Xthesaurus')
806  set thesaurus=Xthesaurus
807  call setline(1, 'mad')
808  call cursor(1, 1)
809  call feedkeys("A\<c-x>\<c-t>\<cr>\<esc>", 'tnix')
810  call assert_equal(['mad', ''], getline(1, '$'))
811  %d
812  call setline(1, 'mad')
813  call cursor(1, 1)
814  call feedkeys("A\<c-x>\<c-t>\<c-n>\<cr>\<esc>", 'tnix')
815  call assert_equal(['angry', ''], getline(1, '$'))
816  %d
817  call setline(1, 'mad')
818  call cursor(1, 1)
819  call feedkeys("A\<c-x>\<c-t>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
820  call assert_equal(['furious', ''], getline(1, '$'))
821  %d
822  call setline(1, 'mad')
823  call cursor(1, 1)
824  call feedkeys("A\<c-x>\<c-t>\<c-n>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
825  call assert_equal(['enraged', ''], getline(1, '$'))
826  %d
827  call setline(1, 'mad')
828  call cursor(1, 1)
829  call feedkeys("A\<c-x>\<c-t>\<c-n>\<c-n>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
830  call assert_equal(['mad', ''], getline(1, '$'))
831  %d
832  call setline(1, 'mad')
833  call cursor(1, 1)
834  call feedkeys("A\<c-x>\<c-t>\<c-n>\<c-n>\<c-n>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
835  call assert_equal(['mad', ''], getline(1, '$'))
836  " Using <c-p> <c-n> when 'complete' is empty
837  set complete=
838  %d
839  call setline(1, 'mad')
840  call cursor(1, 1)
841  call feedkeys("A\<c-x>\<c-t>\<c-n>\<cr>\<esc>", 'tnix')
842  call assert_equal(['angry', ''], getline(1, '$'))
843  %d
844  call setline(1, 'mad')
845  call cursor(1, 1)
846  call feedkeys("A\<c-x>\<c-t>\<c-p>\<cr>\<esc>", 'tnix')
847  call assert_equal(['mad', ''], getline(1, '$'))
848  set complete&
849
850  set thesaurus=
851  %d
852  call setline(1, 'mad')
853  call cursor(1, 1)
854  let v:testing = 1
855  try
856    call feedkeys("A\<c-x>\<c-t>\<esc>", 'tnix')
857  catch
858    " error sleeps 2 seconds, when v:testing is not set
859    let v:testing = 0
860  endtry
861  call assert_equal(['mad'], getline(1, '$'))
862  call delete('Xthesaurus')
863  bw!
864endfunc
865
866func Test_edit_CTRL_U()
867  " Test 'completefunc'
868  new
869  " -1, -2 and -3 are special return values
870  let g:special=0
871  fun! CompleteMonths(findstart, base)
872    if a:findstart
873      " locate the start of the word
874      return g:special
875    else
876      " find months matching with "a:base"
877      let res = []
878      for m in split("Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec")
879        if m =~ '^\c'.a:base
880          call add(res, {'word': m, 'abbr': m.' Month', 'icase': 0})
881        endif
882      endfor
883      return {'words': res, 'refresh': 'always'}
884    endif
885  endfun
886  set completefunc=CompleteMonths
887  call setline(1, ['', ''])
888  call cursor(1, 1)
889  call feedkeys("AX\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
890  call assert_equal(['X', '', ''], getline(1, '$'))
891  %d
892  let g:special=-1
893  call feedkeys("AX\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
894  call assert_equal(['XJan', ''], getline(1, '$'))
895  %d
896  let g:special=-2
897  call feedkeys("AX\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
898  call assert_equal(['X', ''], getline(1, '$'))
899  %d
900  let g:special=-3
901  call feedkeys("AX\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
902  call assert_equal(['X', ''], getline(1, '$'))
903  %d
904  let g:special=0
905  call feedkeys("AM\<c-x>\<c-u>\<cr>\<esc>", 'tnix')
906  call assert_equal(['Mar', ''], getline(1, '$'))
907  %d
908  call feedkeys("AM\<c-x>\<c-u>\<c-n>\<cr>\<esc>", 'tnix')
909  call assert_equal(['May', ''], getline(1, '$'))
910  %d
911  call feedkeys("AM\<c-x>\<c-u>\<c-n>\<c-n>\<cr>\<esc>", 'tnix')
912  call assert_equal(['M', ''], getline(1, '$'))
913  delfu CompleteMonths
914  %d
915  try
916    call feedkeys("A\<c-x>\<c-u>", 'tnix')
917    call assert_fails(1, 'unknown completion function')
918  catch /^Vim\%((\a\+)\)\=:E117/
919    call assert_true(1, 'E117 error caught')
920  endtry
921  set completefunc=
922  bw!
923endfunc
924
925func Test_edit_completefunc_delete()
926  func CompleteFunc(findstart, base)
927    if a:findstart == 1
928      return col('.') - 1
929    endif
930    normal dd
931    return ['a', 'b']
932  endfunc
933  new
934  set completefunc=CompleteFunc
935  call setline(1, ['', 'abcd', ''])
936  2d
937  call assert_fails("normal 2G$a\<C-X>\<C-U>", 'E578:')
938  bwipe!
939endfunc
940
941
942func Test_edit_CTRL_Z()
943  " Ctrl-Z when insertmode is not set inserts it literally
944  new
945  call setline(1, 'abc')
946  call feedkeys("A\<c-z>\<esc>", 'tnix')
947  call assert_equal(["abc\<c-z>"], getline(1,'$'))
948  bw!
949  " TODO: How to Test Ctrl-Z in insert mode, e.g. suspend?
950endfunc
951
952func Test_edit_DROP()
953  CheckFeature dnd
954  new
955  call setline(1, ['abc def ghi'])
956  call cursor(1, 1)
957  try
958    call feedkeys("i\<Drop>\<Esc>", 'tnix')
959    call assert_fails(1, 'Invalid register name')
960  catch /^Vim\%((\a\+)\)\=:E353/
961    call assert_true(1, 'error caught')
962  endtry
963  bw!
964endfunc
965
966func Test_edit_CTRL_V()
967  CheckFeature ebcdic
968  new
969  call setline(1, ['abc'])
970  call cursor(2, 1)
971  " force some redraws
972  set showmode showcmd
973  "call test_override_char_avail(1)
974  call test_override('ALL', 1)
975  call feedkeys("A\<c-v>\<c-n>\<c-v>\<c-l>\<c-v>\<c-b>\<esc>", 'tnix')
976  call assert_equal(["abc\x0e\x0c\x02"], getline(1, '$'))
977
978  if has("rightleft") && exists("+rl")
979    set rl
980    call setline(1, ['abc'])
981    call cursor(2, 1)
982    call feedkeys("A\<c-v>\<c-n>\<c-v>\<c-l>\<c-v>\<c-b>\<esc>", 'tnix')
983    call assert_equal(["abc\x0e\x0c\x02"], getline(1, '$'))
984    set norl
985  endif
986
987  call test_override('ALL', 0)
988  set noshowmode showcmd
989  bw!
990endfunc
991
992func Test_edit_F1()
993  CheckFeature quickfix
994
995  " Pressing <f1>
996  new
997  call feedkeys(":set im\<cr>\<f1>\<c-l>", 'tnix')
998  set noinsertmode
999  call assert_equal('help', &buftype)
1000  bw
1001  bw
1002endfunc
1003
1004func Test_edit_F21()
1005  " Pressing <f21>
1006  " sends a netbeans command
1007  CheckFeature netbeans_intg
1008  new
1009  " I have no idea what this is supposed to do :)
1010  call feedkeys("A\<F21>\<F1>\<esc>", 'tnix')
1011  bw
1012endfunc
1013
1014func Test_edit_HOME_END()
1015  " Test Home/End Keys
1016  new
1017  set foldopen+=hor
1018  call setline(1, ['abc', 'def'])
1019  call cursor(1, 1)
1020  call feedkeys("AX\<Home>Y\<esc>", 'tnix')
1021  call cursor(2, 1)
1022  call feedkeys("iZ\<End>Y\<esc>", 'tnix')
1023  call assert_equal(['YabcX', 'ZdefY'], getline(1, '$'))
1024
1025  set foldopen-=hor
1026  bw!
1027endfunc
1028
1029func Test_edit_INS()
1030  " Test for Pressing <Insert>
1031  new
1032  call setline(1, ['abc', 'def'])
1033  call cursor(1, 1)
1034  call feedkeys("i\<Insert>ZYX>", 'tnix')
1035  call assert_equal(['ZYX>', 'def'], getline(1, '$'))
1036  call setline(1, ['abc', 'def'])
1037  call cursor(1, 1)
1038  call feedkeys("i\<Insert>Z\<Insert>YX>", 'tnix')
1039  call assert_equal(['ZYX>bc', 'def'], getline(1, '$'))
1040  bw!
1041endfunc
1042
1043func Test_edit_LEFT_RIGHT()
1044  " Left, Shift-Left, Right, Shift-Right
1045  new
1046  call setline(1, ['abc def ghi', 'ABC DEF GHI', 'ZZZ YYY XXX'])
1047  let _ww=&ww
1048  set ww=
1049  call cursor(2, 1)
1050  call feedkeys("i\<left>\<esc>", 'tnix')
1051  call assert_equal([0, 2, 1, 0], getpos('.'))
1052  " Is this a bug, <s-left> does not respect whichwrap option
1053  call feedkeys("i\<s-left>\<esc>", 'tnix')
1054  call assert_equal([0, 1, 8, 0], getpos('.'))
1055  call feedkeys("i". repeat("\<s-left>", 3). "\<esc>", 'tnix')
1056  call assert_equal([0, 1, 1, 0], getpos('.'))
1057  call feedkeys("i\<right>\<esc>", 'tnix')
1058  call assert_equal([0, 1, 1, 0], getpos('.'))
1059  call feedkeys("i\<right>\<right>\<esc>", 'tnix')
1060  call assert_equal([0, 1, 2, 0], getpos('.'))
1061  call feedkeys("A\<right>\<esc>", 'tnix')
1062  call assert_equal([0, 1, 11, 0], getpos('.'))
1063  call feedkeys("A\<s-right>\<esc>", 'tnix')
1064  call assert_equal([0, 2, 1, 0], getpos('.'))
1065  call feedkeys("i\<s-right>\<esc>", 'tnix')
1066  call assert_equal([0, 2, 4, 0], getpos('.'))
1067  call cursor(3, 11)
1068  call feedkeys("A\<right>\<esc>", 'tnix')
1069  call feedkeys("A\<s-right>\<esc>", 'tnix')
1070  call assert_equal([0, 3, 11, 0], getpos('.'))
1071  call cursor(2, 11)
1072  " <S-Right> does not respect 'whichwrap' option
1073  call feedkeys("A\<s-right>\<esc>", 'tnix')
1074  call assert_equal([0, 3, 1, 0], getpos('.'))
1075  " Check motion when 'whichwrap' contains cursor keys for insert mode
1076  set ww+=[,]
1077  call cursor(2, 1)
1078  call feedkeys("i\<left>\<esc>", 'tnix')
1079  call assert_equal([0, 1, 11, 0], getpos('.'))
1080  call cursor(2, 11)
1081  call feedkeys("A\<right>\<esc>", 'tnix')
1082  call assert_equal([0, 3, 1, 0], getpos('.'))
1083  call cursor(2, 11)
1084  call feedkeys("A\<s-right>\<esc>", 'tnix')
1085  call assert_equal([0, 3, 1, 0], getpos('.'))
1086  let &ww = _ww
1087  bw!
1088endfunc
1089
1090func Test_edit_MOUSE()
1091  " This is a simple test, since we not really using the mouse here
1092  CheckFeature mouse
1093  10new
1094  call setline(1, range(1, 100))
1095  call cursor(1, 1)
1096  set mouse=a
1097  call feedkeys("A\<ScrollWheelDown>\<esc>", 'tnix')
1098  call assert_equal([0, 4, 1, 0], getpos('.'))
1099  " This should move by one pageDown, but only moves
1100  " by one line when the test is run...
1101  call feedkeys("A\<S-ScrollWheelDown>\<esc>", 'tnix')
1102  call assert_equal([0, 5, 1, 0], getpos('.'))
1103  set nostartofline
1104  call feedkeys("A\<C-ScrollWheelDown>\<esc>", 'tnix')
1105  call assert_equal([0, 6, 1, 0], getpos('.'))
1106  call feedkeys("A\<LeftMouse>\<esc>", 'tnix')
1107  call assert_equal([0, 6, 1, 0], getpos('.'))
1108  call feedkeys("A\<RightMouse>\<esc>", 'tnix')
1109  call assert_equal([0, 6, 1, 0], getpos('.'))
1110  call cursor(1, 100)
1111  norm! zt
1112  " this should move by a screen up, but when the test
1113  " is run, it moves up to the top of the buffer...
1114  call feedkeys("A\<ScrollWheelUp>\<esc>", 'tnix')
1115  call assert_equal([0, 1, 1, 0], getpos('.'))
1116  call cursor(1, 30)
1117  norm! zt
1118  call feedkeys("A\<S-ScrollWheelUp>\<esc>", 'tnix')
1119  call assert_equal([0, 1, 1, 0], getpos('.'))
1120  call cursor(1, 30)
1121  norm! zt
1122  call feedkeys("A\<C-ScrollWheelUp>\<esc>", 'tnix')
1123  call assert_equal([0, 1, 1, 0], getpos('.'))
1124  %d
1125  call setline(1, repeat(["12345678901234567890"], 100))
1126  call cursor(2, 1)
1127  call feedkeys("A\<ScrollWheelRight>\<esc>", 'tnix')
1128  call assert_equal([0, 2, 20, 0], getpos('.'))
1129  call feedkeys("A\<ScrollWheelLeft>\<esc>", 'tnix')
1130  call assert_equal([0, 2, 20, 0], getpos('.'))
1131  call feedkeys("A\<S-ScrollWheelRight>\<esc>", 'tnix')
1132  call assert_equal([0, 2, 20, 0], getpos('.'))
1133  call feedkeys("A\<S-ScrollWheelLeft>\<esc>", 'tnix')
1134  call assert_equal([0, 2, 20, 0], getpos('.'))
1135  call feedkeys("A\<C-ScrollWheelRight>\<esc>", 'tnix')
1136  call assert_equal([0, 2, 20, 0], getpos('.'))
1137  call feedkeys("A\<C-ScrollWheelLeft>\<esc>", 'tnix')
1138  call assert_equal([0, 2, 20, 0], getpos('.'))
1139  set mouse& startofline
1140  bw!
1141endfunc
1142
1143func Test_edit_PAGEUP_PAGEDOWN()
1144  10new
1145  call setline(1, repeat(['abc def ghi'], 30))
1146  call cursor(1, 1)
1147  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1148  call assert_equal([0, 9, 1, 0], getpos('.'))
1149  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1150  call assert_equal([0, 17, 1, 0], getpos('.'))
1151  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1152  call assert_equal([0, 25, 1, 0], getpos('.'))
1153  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1154  call assert_equal([0, 30, 1, 0], getpos('.'))
1155  call feedkeys("i\<PageDown>\<esc>", 'tnix')
1156  call assert_equal([0, 30, 1, 0], getpos('.'))
1157  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1158  call assert_equal([0, 29, 1, 0], getpos('.'))
1159  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1160  call assert_equal([0, 21, 1, 0], getpos('.'))
1161  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1162  call assert_equal([0, 13, 1, 0], getpos('.'))
1163  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1164  call assert_equal([0, 5, 1, 0], getpos('.'))
1165  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1166  call assert_equal([0, 5, 11, 0], getpos('.'))
1167  " <S-Up> is the same as <PageUp>
1168  " <S-Down> is the same as <PageDown>
1169  call cursor(1, 1)
1170  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1171  call assert_equal([0, 9, 1, 0], getpos('.'))
1172  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1173  call assert_equal([0, 17, 1, 0], getpos('.'))
1174  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1175  call assert_equal([0, 25, 1, 0], getpos('.'))
1176  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1177  call assert_equal([0, 30, 1, 0], getpos('.'))
1178  call feedkeys("i\<S-Down>\<esc>", 'tnix')
1179  call assert_equal([0, 30, 1, 0], getpos('.'))
1180  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1181  call assert_equal([0, 29, 1, 0], getpos('.'))
1182  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1183  call assert_equal([0, 21, 1, 0], getpos('.'))
1184  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1185  call assert_equal([0, 13, 1, 0], getpos('.'))
1186  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1187  call assert_equal([0, 5, 1, 0], getpos('.'))
1188  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1189  call assert_equal([0, 5, 11, 0], getpos('.'))
1190  set nostartofline
1191  call cursor(30, 11)
1192  norm! zt
1193  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1194  call assert_equal([0, 29, 11, 0], getpos('.'))
1195  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1196  call assert_equal([0, 21, 11, 0], getpos('.'))
1197  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1198  call assert_equal([0, 13, 11, 0], getpos('.'))
1199  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1200  call assert_equal([0, 5, 11, 0], getpos('.'))
1201  call feedkeys("A\<PageUp>\<esc>", 'tnix')
1202  call assert_equal([0, 5, 11, 0], getpos('.'))
1203  call cursor(1, 1)
1204  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1205  call assert_equal([0, 9, 11, 0], getpos('.'))
1206  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1207  call assert_equal([0, 17, 11, 0], getpos('.'))
1208  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1209  call assert_equal([0, 25, 11, 0], getpos('.'))
1210  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1211  call assert_equal([0, 30, 11, 0], getpos('.'))
1212  call feedkeys("A\<PageDown>\<esc>", 'tnix')
1213  call assert_equal([0, 30, 11, 0], getpos('.'))
1214  " <S-Up> is the same as <PageUp>
1215  " <S-Down> is the same as <PageDown>
1216  call cursor(30, 11)
1217  norm! zt
1218  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1219  call assert_equal([0, 29, 11, 0], getpos('.'))
1220  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1221  call assert_equal([0, 21, 11, 0], getpos('.'))
1222  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1223  call assert_equal([0, 13, 11, 0], getpos('.'))
1224  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1225  call assert_equal([0, 5, 11, 0], getpos('.'))
1226  call feedkeys("A\<S-Up>\<esc>", 'tnix')
1227  call assert_equal([0, 5, 11, 0], getpos('.'))
1228  call cursor(1, 1)
1229  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1230  call assert_equal([0, 9, 11, 0], getpos('.'))
1231  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1232  call assert_equal([0, 17, 11, 0], getpos('.'))
1233  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1234  call assert_equal([0, 25, 11, 0], getpos('.'))
1235  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1236  call assert_equal([0, 30, 11, 0], getpos('.'))
1237  call feedkeys("A\<S-Down>\<esc>", 'tnix')
1238  call assert_equal([0, 30, 11, 0], getpos('.'))
1239  bw!
1240endfunc
1241
1242func Test_edit_forbidden()
1243  new
1244  " 1) edit in the sandbox is not allowed
1245  call setline(1, 'a')
1246  com! Sandbox :sandbox call feedkeys("i\<del>\<esc>", 'tnix')
1247  call assert_fails(':Sandbox', 'E48:')
1248  com! Sandbox :sandbox exe "norm! i\<del>"
1249  call assert_fails(':Sandbox', 'E48:')
1250  delcom Sandbox
1251  call assert_equal(['a'], getline(1,'$'))
1252  " 2) edit with textlock set
1253  fu! DoIt()
1254    call feedkeys("i\<del>\<esc>", 'tnix')
1255  endfu
1256  au InsertCharPre <buffer> :call DoIt()
1257  try
1258    call feedkeys("ix\<esc>", 'tnix')
1259    call assert_fails(1, 'textlock')
1260  catch /^Vim\%((\a\+)\)\=:E565/ " catch E565: not allowed here
1261  endtry
1262  " TODO: Might be a bug: should x really be inserted here
1263  call assert_equal(['xa'], getline(1, '$'))
1264  delfu DoIt
1265  try
1266    call feedkeys("ix\<esc>", 'tnix')
1267    call assert_fails(1, 'unknown function')
1268  catch /^Vim\%((\a\+)\)\=:E117/ " catch E117: unknown function
1269  endtry
1270  au! InsertCharPre
1271  " 3) edit when completion is shown
1272  fun! Complete(findstart, base)
1273    if a:findstart
1274      return col('.')
1275    else
1276      call feedkeys("i\<del>\<esc>", 'tnix')
1277      return []
1278    endif
1279  endfun
1280  set completefunc=Complete
1281  try
1282    call feedkeys("i\<c-x>\<c-u>\<esc>", 'tnix')
1283    call assert_fails(1, 'change in complete function')
1284  catch /^Vim\%((\a\+)\)\=:E565/ " catch E565
1285  endtry
1286  delfu Complete
1287  set completefunc=
1288  if has("rightleft") && exists("+fkmap")
1289    " 4) 'R' when 'fkmap' and 'revins' is set.
1290    set revins fkmap
1291    try
1292      normal Ri
1293      call assert_fails(1, "R with 'fkmap' and 'ri' set")
1294    catch
1295    finally
1296      set norevins nofkmap
1297    endtry
1298  endif
1299  bw!
1300endfunc
1301
1302func Test_edit_rightleft()
1303  " Cursor in rightleft mode moves differently
1304  CheckFeature rightleft
1305  call NewWindow(10, 20)
1306  call setline(1, ['abc', 'def', 'ghi'])
1307  call cursor(1, 2)
1308  set rightleft
1309  " Screen looks as expected
1310  let lines = ScreenLines([1, 4], winwidth(0))
1311  let expect = [
1312        \"                 cba",
1313        \"                 fed",
1314        \"                 ihg",
1315        \"                   ~"]
1316  call assert_equal(join(expect, "\n"), join(lines, "\n"))
1317  " 2) right moves to the left
1318  call feedkeys("i\<right>\<esc>x", 'txin')
1319  call assert_equal(['bc', 'def', 'ghi'], getline(1,'$'))
1320  call cursor(1, 2)
1321  call feedkeys("i\<s-right>\<esc>", 'txin')
1322  call cursor(1, 2)
1323  call feedkeys("i\<c-right>\<esc>", 'txin')
1324  " Screen looks as expected
1325  let lines = ScreenLines([1, 4], winwidth(0))
1326  let expect = [
1327        \"                  cb",
1328        \"                 fed",
1329        \"                 ihg",
1330        \"                   ~"]
1331  call assert_equal(join(expect, "\n"), join(lines, "\n"))
1332  " 2) left moves to the right
1333  call setline(1, ['abc', 'def', 'ghi'])
1334  call cursor(1, 2)
1335  call feedkeys("i\<left>\<esc>x", 'txin')
1336  call assert_equal(['ac', 'def', 'ghi'], getline(1,'$'))
1337  call cursor(1, 2)
1338  call feedkeys("i\<s-left>\<esc>", 'txin')
1339  call cursor(1, 2)
1340  call feedkeys("i\<c-left>\<esc>", 'txin')
1341  " Screen looks as expected
1342  let lines = ScreenLines([1, 4], winwidth(0))
1343  let expect = [
1344        \"                  ca",
1345        \"                 fed",
1346        \"                 ihg",
1347        \"                   ~"]
1348  call assert_equal(join(expect, "\n"), join(lines, "\n"))
1349  %d _
1350  call test_override('redraw_flag', 1)
1351  call test_override('char_avail', 1)
1352  call feedkeys("a\<C-V>x41", "xt")
1353  redraw!
1354  call assert_equal(repeat(' ', 19) .. 'A', Screenline(1))
1355  call test_override('ALL', 0)
1356  set norightleft
1357  bw!
1358endfunc
1359
1360func Test_edit_complete_very_long_name()
1361  " Long directory names only work on Unix.
1362  CheckUnix
1363
1364  let dirname = getcwd() . "/Xdir"
1365  let longdirname = dirname . repeat('/' . repeat('d', 255), 4)
1366  try
1367    call mkdir(longdirname, 'p')
1368  catch /E739:/
1369    " Long directory name probably not supported.
1370    call delete(dirname, 'rf')
1371    return
1372  endtry
1373
1374  " Try to get the Vim window position before setting 'columns', so that we can
1375  " move the window back to where it was.
1376  let winposx = getwinposx()
1377  let winposy = getwinposy()
1378
1379  if winposx >= 0 && winposy >= 0 && !has('gui_running')
1380    " We did get the window position, but xterm may report the wrong numbers.
1381    " Move the window to the reported position and compute any offset.
1382    exe 'winpos ' . winposx . ' ' . winposy
1383    sleep 100m
1384    let x = getwinposx()
1385    if x >= 0
1386      let winposx += winposx - x
1387    endif
1388    let y = getwinposy()
1389    if y >= 0
1390      let winposy += winposy - y
1391    endif
1392  endif
1393
1394  let save_columns = &columns
1395  " Need at least about 1100 columns to reproduce the problem.
1396  set columns=2000
1397  set noswapfile
1398
1399  let longfilename = longdirname . '/' . repeat('a', 255)
1400  call writefile(['Totum', 'Table'], longfilename)
1401  new
1402  exe "next Xfile " . longfilename
1403  exe "normal iT\<C-N>"
1404
1405  bwipe!
1406  exe 'bwipe! ' . longfilename
1407  call delete(dirname, 'rf')
1408  let &columns = save_columns
1409  if winposx >= 0 && winposy >= 0
1410    exe 'winpos ' . winposx . ' ' . winposy
1411  endif
1412  set swapfile&
1413endfunc
1414
1415func Test_edit_backtick()
1416  next a\`b c
1417  call assert_equal('a`b', expand('%'))
1418  next
1419  call assert_equal('c', expand('%'))
1420  call assert_equal('a\`b c', expand('##'))
1421endfunc
1422
1423func Test_edit_quit()
1424  edit foo.txt
1425  split
1426  new
1427  call setline(1, 'hello')
1428  3wincmd w
1429  redraw!
1430  call assert_fails('1q', 'E37:')
1431  bwipe! foo.txt
1432  only
1433endfunc
1434
1435func Test_edit_alt()
1436  " Keeping the cursor line didn't happen when the first line has indent.
1437  new
1438  call setline(1, ['  one', 'two', 'three'])
1439  w XAltFile
1440  $
1441  call assert_equal(3, line('.'))
1442  e Xother
1443  e #
1444  call assert_equal(3, line('.'))
1445
1446  bwipe XAltFile
1447  call delete('XAltFile')
1448endfunc
1449
1450func Test_edit_InsertLeave()
1451  new
1452  au InsertLeavePre * let g:did_au_pre = 1
1453  au InsertLeave * let g:did_au = 1
1454  let g:did_au_pre = 0
1455  let g:did_au = 0
1456  call feedkeys("afoo\<Esc>", 'tx')
1457  call assert_equal(1, g:did_au_pre)
1458  call assert_equal(1, g:did_au)
1459  call assert_equal('foo', getline(1))
1460
1461  let g:did_au_pre = 0
1462  let g:did_au = 0
1463  call feedkeys("Sbar\<C-C>", 'tx')
1464  call assert_equal(1, g:did_au_pre)
1465  call assert_equal(0, g:did_au)
1466  call assert_equal('bar', getline(1))
1467
1468  inoremap x xx<Esc>
1469  let g:did_au_pre = 0
1470  let g:did_au = 0
1471  call feedkeys("Saax", 'tx')
1472  call assert_equal(1, g:did_au_pre)
1473  call assert_equal(1, g:did_au)
1474  call assert_equal('aaxx', getline(1))
1475
1476  inoremap x xx<C-C>
1477  let g:did_au_pre = 0
1478  let g:did_au = 0
1479  call feedkeys("Sbbx", 'tx')
1480  call assert_equal(1, g:did_au_pre)
1481  call assert_equal(0, g:did_au)
1482  call assert_equal('bbxx', getline(1))
1483
1484  bwipe!
1485  au! InsertLeave InsertLeavePre
1486  iunmap x
1487endfunc
1488
1489func Test_edit_InsertLeave_undo()
1490  new XtestUndo
1491  set undofile
1492  au InsertLeave * wall
1493  exe "normal ofoo\<Esc>"
1494  call assert_equal(2, line('$'))
1495  normal u
1496  call assert_equal(1, line('$'))
1497
1498  bwipe!
1499  au! InsertLeave
1500  call delete('XtestUndo')
1501  call delete(undofile('XtestUndo'))
1502  set undofile&
1503endfunc
1504
1505" Test for inserting characters using CTRL-V followed by a number.
1506func Test_edit_special_chars()
1507  new
1508
1509  if has("ebcdic")
1510    let t = "o\<C-V>193\<C-V>xc2\<C-V>o303 \<C-V>90a\<C-V>xfg\<C-V>o578\<Esc>"
1511  else
1512    let t = "o\<C-V>65\<C-V>x42\<C-V>o103 \<C-V>33a\<C-V>xfg\<C-V>o78\<Esc>"
1513  endif
1514
1515  exe "normal " . t
1516  call assert_equal("ABC !a\<C-O>g\<C-G>8", getline(2))
1517
1518  close!
1519endfunc
1520
1521func Test_edit_startinsert()
1522  new
1523  set backspace+=start
1524  call setline(1, 'foobar')
1525  call feedkeys("A\<C-U>\<Esc>", 'xt')
1526  call assert_equal('', getline(1))
1527
1528  call setline(1, 'foobar')
1529  call feedkeys(":startinsert!\<CR>\<C-U>\<Esc>", 'xt')
1530  call assert_equal('', getline(1))
1531
1532  set backspace&
1533  bwipe!
1534endfunc
1535
1536" Test for :startreplace and :startgreplace
1537func Test_edit_startreplace()
1538  new
1539  call setline(1, 'abc')
1540  call feedkeys("l:startreplace\<CR>xyz\e", 'xt')
1541  call assert_equal('axyz', getline(1))
1542  call feedkeys("0:startreplace!\<CR>abc\e", 'xt')
1543  call assert_equal('axyzabc', getline(1))
1544  call setline(1, "a\tb")
1545  call feedkeys("0l:startgreplace\<CR>xyz\e", 'xt')
1546  call assert_equal("axyz\tb", getline(1))
1547  call feedkeys("0i\<C-R>=execute('startreplace')\<CR>12\e", 'xt')
1548  call assert_equal("12axyz\tb", getline(1))
1549  close!
1550endfunc
1551
1552func Test_edit_noesckeys()
1553  CheckNotGui
1554  new
1555
1556  " <Left> moves cursor when 'esckeys' is set
1557  exe "set t_kl=\<Esc>OD"
1558  set esckeys
1559  call feedkeys("axyz\<Esc>ODX", "xt")
1560  call assert_equal("xyXz", getline(1))
1561
1562  " <Left> exits Insert mode when 'esckeys' is off
1563  set noesckeys
1564  call setline(1, '')
1565  call feedkeys("axyz\<Esc>ODX", "xt")
1566  call assert_equal(["DX", "xyz"], getline(1, 2))
1567
1568  bwipe!
1569  set esckeys
1570endfunc
1571
1572" Test for running an invalid ex command in insert mode using CTRL-O
1573func Test_edit_ctrl_o_invalid_cmd()
1574  new
1575  set showmode showcmd
1576  " Avoid a sleep of 3 seconds. Zero might have side effects.
1577  call test_override('ui_delay', 50)
1578  let caught_e492 = 0
1579  try
1580    call feedkeys("i\<C-O>:invalid\<CR>abc\<Esc>", "xt")
1581  catch /E492:/
1582    let caught_e492 = 1
1583  endtry
1584  call assert_equal(1, caught_e492)
1585  call assert_equal('abc', getline(1))
1586  set showmode& showcmd&
1587  call test_override('ui_delay', 0)
1588  close!
1589endfunc
1590
1591" Test for editing a file with a very long name
1592func Test_edit_illegal_filename()
1593  CheckEnglish
1594  new
1595  redir => msg
1596  exe 'edit ' . repeat('f', 5000)
1597  redir END
1598  call assert_match("Illegal file name$", split(msg, "\n")[0])
1599  close!
1600endfunc
1601
1602" Test for editing a directory
1603func Test_edit_is_a_directory()
1604  CheckEnglish
1605  let dirname = getcwd() . "/Xdir"
1606  call mkdir(dirname, 'p')
1607
1608  new
1609  redir => msg
1610  exe 'edit' dirname
1611  redir END
1612  call assert_match("is a directory$", split(msg, "\n")[0])
1613  bwipe!
1614
1615  let dirname .= '/'
1616
1617  new
1618  redir => msg
1619  exe 'edit' dirname
1620  redir END
1621  call assert_match("is a directory$", split(msg, "\n")[0])
1622  bwipe!
1623
1624  call delete(dirname, 'rf')
1625endfunc
1626
1627" Test for editing a file using invalid file encoding
1628func Test_edit_invalid_encoding()
1629  CheckEnglish
1630  call writefile([], 'Xfile')
1631  redir => msg
1632  new ++enc=axbyc Xfile
1633  redir END
1634  call assert_match('\[NOT converted\]', msg)
1635  call delete('Xfile')
1636  close!
1637endfunc
1638
1639" Test for the "charconvert" option
1640func Test_edit_charconvert()
1641  CheckEnglish
1642  call writefile(['one', 'two'], 'Xfile')
1643
1644  " set 'charconvert' to a non-existing function
1645  set charconvert=NonExitingFunc()
1646  new
1647  let caught_e117 = v:false
1648  try
1649    redir => msg
1650    edit ++enc=axbyc Xfile
1651  catch /E117:/
1652    let caught_e117 = v:true
1653  finally
1654    redir END
1655  endtry
1656  call assert_true(caught_e117)
1657  call assert_equal(['one', 'two'], getline(1, '$'))
1658  call assert_match("Conversion with 'charconvert' failed", msg)
1659  close!
1660  set charconvert&
1661
1662  " 'charconvert' function doesn't create a output file
1663  func Cconv1()
1664  endfunc
1665  set charconvert=Cconv1()
1666  new
1667  redir => msg
1668  edit ++enc=axbyc Xfile
1669  redir END
1670  call assert_equal(['one', 'two'], getline(1, '$'))
1671  call assert_match("can't read output of 'charconvert'", msg)
1672  close!
1673  delfunc Cconv1
1674  set charconvert&
1675
1676  " 'charconvert' function to convert to upper case
1677  func Cconv2()
1678    let data = readfile(v:fname_in)
1679    call map(data, 'toupper(v:val)')
1680    call writefile(data, v:fname_out)
1681  endfunc
1682  set charconvert=Cconv2()
1683  new Xfile
1684  write ++enc=ucase Xfile1
1685  call assert_equal(['ONE', 'TWO'], readfile('Xfile1'))
1686  call delete('Xfile1')
1687  close!
1688  delfunc Cconv2
1689  set charconvert&
1690
1691  " 'charconvert' function removes the input file
1692  func Cconv3()
1693    call delete(v:fname_in)
1694  endfunc
1695  set charconvert=Cconv3()
1696  new
1697  call assert_fails('edit ++enc=lcase Xfile', 'E202:')
1698  call assert_equal([''], getline(1, '$'))
1699  close!
1700  delfunc Cconv3
1701  set charconvert&
1702
1703  call delete('Xfile')
1704endfunc
1705
1706" Test for editing a file without read permission
1707func Test_edit_file_no_read_perm()
1708  CheckUnix
1709  call writefile(['one', 'two'], 'Xfile')
1710  call setfperm('Xfile', '-w-------')
1711  new
1712  redir => msg
1713  edit Xfile
1714  redir END
1715  call assert_equal(1, &readonly)
1716  call assert_equal([''], getline(1, '$'))
1717  call assert_match('\[Permission Denied\]', msg)
1718  close!
1719  call delete('Xfile')
1720endfunc
1721
1722" Pressing escape in 'insertmode' should beep
1723func Test_edit_insertmode_esc_beeps()
1724  new
1725  set insertmode
1726  call assert_beeps("call feedkeys(\"one\<Esc>\", 'xt')")
1727  set insertmode&
1728  " unsupported CTRL-G command should beep in insert mode.
1729  call assert_beeps("normal i\<C-G>l")
1730  close!
1731endfunc
1732
1733" Test for 'hkmap' and 'hkmapp'
1734func Test_edit_hkmap()
1735  CheckFeature rightleft
1736  if has('win32') && !has('gui')
1737    throw 'Skipped: fails on the MS-Windows terminal version'
1738  endif
1739  new
1740
1741  set revins hkmap
1742  let str = 'abcdefghijklmnopqrstuvwxyz'
1743  let str ..= 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'
1744  let str ..= '`/'',.;'
1745  call feedkeys('i' .. str, 'xt')
1746  let expected = "óõú,.;"
1747  let expected ..= "ZYXWVUTSRQPONMLKJIHGFEDCBA"
1748  let expected ..= "æèñ'äåàãø/ôíîöêìçïéòë÷âáðù"
1749  call assert_equal(expected, getline(1))
1750
1751  %d
1752  set revins hkmap hkmapp
1753  let str = 'abcdefghijklmnopqrstuvwxyz'
1754  let str ..= 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'
1755  call feedkeys('i' .. str, 'xt')
1756  let expected = "õYXWVUTSRQóOïíLKJIHGFEDêBA"
1757  let expected ..= "öòXùåèúæø'ôñðîì÷çéäâóǟãëáà"
1758  call assert_equal(expected, getline(1))
1759
1760  set revins& hkmap& hkmapp&
1761  close!
1762endfunc
1763
1764" Test for 'allowrevins' and using CTRL-_ in insert mode
1765func Test_edit_allowrevins()
1766  CheckFeature rightleft
1767  new
1768  set allowrevins
1769  call feedkeys("iABC\<C-_>DEF\<C-_>GHI", 'xt')
1770  call assert_equal('ABCFEDGHI', getline(1))
1771  set allowrevins&
1772  close!
1773endfunc
1774
1775" Test for inserting a register in insert mode using CTRL-R
1776func Test_edit_insert_reg()
1777  new
1778  let g:Line = ''
1779  func SaveFirstLine()
1780    let g:Line = Screenline(1)
1781    return 'r'
1782  endfunc
1783  inoremap <expr> <buffer> <F2> SaveFirstLine()
1784  call test_override('redraw_flag', 1)
1785  call test_override('char_avail', 1)
1786  let @r = 'sample'
1787  call feedkeys("a\<C-R>=SaveFirstLine()\<CR>", "xt")
1788  call assert_equal('"', g:Line)
1789  call test_override('ALL', 0)
1790  close!
1791endfunc
1792
1793" When a character is inserted at the last position of the last line in a
1794" window, the window contents should be scrolled one line up. If the top line
1795" is part of a fold, then the entire fold should be scrolled up.
1796func Test_edit_lastline_scroll()
1797  new
1798  let h = winheight(0)
1799  let lines = ['one', 'two', 'three']
1800  let lines += repeat(['vim'], h - 4)
1801  call setline(1, lines)
1802  call setline(h, repeat('x', winwidth(0) - 1))
1803  call feedkeys("GAx", 'xt')
1804  redraw!
1805  call assert_equal(h - 1, winline())
1806  call assert_equal(2, line('w0'))
1807
1808  " scroll with a fold
1809  1,2fold
1810  normal gg
1811  call setline(h + 1, repeat('x', winwidth(0) - 1))
1812  call feedkeys("GAx", 'xt')
1813  redraw!
1814  call assert_equal(h - 1, winline())
1815  call assert_equal(3, line('w0'))
1816
1817  close!
1818endfunc
1819
1820func Test_edit_browse()
1821  " in the GUI this opens a file picker, we only test the terminal behavior
1822  CheckNotGui
1823
1824  " ":browse xxx" checks for the FileExplorer augroup and assumes editing "."
1825  " works then.
1826  augroup FileExplorer
1827    au!
1828  augroup END
1829
1830  " When the USE_FNAME_CASE is defined this used to cause a crash.
1831  browse enew
1832  bwipe!
1833
1834  browse split
1835  bwipe!
1836endfunc
1837
1838func Test_read_invalid()
1839  set encoding=latin1
1840  " This was not properly checking for going past the end.
1841  call assert_fails('r`=', 'E484')
1842  set encoding=utf-8
1843endfunc
1844
1845" vim: shiftwidth=2 sts=2 expandtab
1846