1" Tests for diff mode
2source shared.vim
3source screendump.vim
4source check.vim
5
6func Test_diff_fold_sync()
7  enew!
8  let g:update_count = 0
9  au DiffUpdated * let g:update_count += 1
10
11  let l = range(50)
12  call setline(1, l)
13  diffthis
14  let winone = win_getid()
15  new
16  let l[25] = 'diff'
17  call setline(1, l)
18  diffthis
19  let wintwo = win_getid()
20  " line 15 is inside the closed fold
21  call assert_equal(19, foldclosedend(10))
22  call win_gotoid(winone)
23  call assert_equal(19, foldclosedend(10))
24  " open the fold
25  normal zv
26  call assert_equal(-1, foldclosedend(10))
27  " fold in other window must have opened too
28  call win_gotoid(wintwo)
29  call assert_equal(-1, foldclosedend(10))
30
31  " cursor position is in sync
32  normal 23G
33  call win_gotoid(winone)
34  call assert_equal(23, getcurpos()[1])
35
36  call assert_equal(1, g:update_count)
37  au! DiffUpdated
38
39  windo diffoff
40  close!
41  set nomodified
42endfunc
43
44func Test_vert_split()
45  set diffopt=filler
46  call Common_vert_split()
47  set diffopt&
48endfunc
49
50func Test_vert_split_internal()
51  set diffopt=internal,filler
52  call Common_vert_split()
53  set diffopt&
54endfunc
55
56func Common_vert_split()
57  " Disable the title to avoid xterm keeping the wrong one.
58  set notitle noicon
59  new
60  let l = ['1 aa', '2 bb', '3 cc', '4 dd', '5 ee']
61  call setline(1, l)
62  w! Xtest
63  normal dd
64  $
65  put
66  normal kkrXoxxx
67  w! Xtest2
68  file Nop
69  normal ggoyyyjjjozzzz
70  set foldmethod=marker foldcolumn=4
71  call assert_equal(0, &diff)
72  call assert_equal('marker', &foldmethod)
73  call assert_equal(4, &foldcolumn)
74  call assert_equal(0, &scrollbind)
75  call assert_equal(0, &cursorbind)
76  call assert_equal(1, &wrap)
77
78  vert diffsplit Xtest
79  vert diffsplit Xtest2
80  call assert_equal(1, &diff)
81  call assert_equal('diff', &foldmethod)
82  call assert_equal(2, &foldcolumn)
83  call assert_equal(1, &scrollbind)
84  call assert_equal(1, &cursorbind)
85  call assert_equal(0, &wrap)
86
87  let diff_fdm = &fdm
88  let diff_fdc = &fdc
89  " repeat entering diff mode here to see if this saves the wrong settings
90  diffthis
91  " jump to second window for a moment to have filler line appear at start of
92  " first window
93  wincmd w
94  normal gg
95  wincmd p
96  normal gg
97  call assert_equal(2, winline())
98  normal j
99  call assert_equal(4, winline())
100  normal j
101  call assert_equal(5, winline())
102  normal j
103  call assert_equal(6, winline())
104  normal j
105  call assert_equal(8, winline())
106  normal j
107  call assert_equal(9, winline())
108
109  wincmd w
110  normal gg
111  call assert_equal(1, winline())
112  normal j
113  call assert_equal(2, winline())
114  normal j
115  call assert_equal(4, winline())
116  normal j
117  call assert_equal(5, winline())
118  normal j
119  call assert_equal(8, winline())
120
121  wincmd w
122  normal gg
123  call assert_equal(2, winline())
124  normal j
125  call assert_equal(3, winline())
126  normal j
127  call assert_equal(4, winline())
128  normal j
129  call assert_equal(5, winline())
130  normal j
131  call assert_equal(6, winline())
132  normal j
133  call assert_equal(7, winline())
134  normal j
135  call assert_equal(8, winline())
136
137  " Test diffoff
138  diffoff!
139  1wincmd 2
140  let &diff = 1
141  let &fdm = diff_fdm
142  let &fdc = diff_fdc
143  4wincmd w
144  diffoff!
145  1wincmd w
146  call assert_equal(0, &diff)
147  call assert_equal('marker', &foldmethod)
148  call assert_equal(4, &foldcolumn)
149  call assert_equal(0, &scrollbind)
150  call assert_equal(0, &cursorbind)
151  call assert_equal(1, &wrap)
152
153  wincmd w
154  call assert_equal(0, &diff)
155  call assert_equal('marker', &foldmethod)
156  call assert_equal(4, &foldcolumn)
157  call assert_equal(0, &scrollbind)
158  call assert_equal(0, &cursorbind)
159  call assert_equal(1, &wrap)
160
161  wincmd w
162  call assert_equal(0, &diff)
163  call assert_equal('marker', &foldmethod)
164  call assert_equal(4, &foldcolumn)
165  call assert_equal(0, &scrollbind)
166  call assert_equal(0, &cursorbind)
167  call assert_equal(1, &wrap)
168
169  call delete('Xtest')
170  call delete('Xtest2')
171  windo bw!
172endfunc
173
174func Test_filler_lines()
175  " Test that diffing shows correct filler lines
176  enew!
177  put =range(4,10)
178  1d _
179  vnew
180  put =range(1,10)
181  1d _
182  windo diffthis
183  wincmd h
184  call assert_equal(1, line('w0'))
185  unlet! diff_fdm diff_fdc
186  windo diffoff
187  bwipe!
188  enew!
189endfunc
190
191func Test_diffget_diffput()
192  enew!
193  let l = range(50)
194  call setline(1, l)
195  call assert_fails('diffget', 'E99:')
196  diffthis
197  call assert_fails('diffget', 'E100:')
198  new
199  let l[10] = 'one'
200  let l[20] = 'two'
201  let l[30] = 'three'
202  let l[40] = 'four'
203  call setline(1, l)
204  diffthis
205  call assert_equal('one', getline(11))
206  11diffget
207  call assert_equal('10', getline(11))
208  21diffput
209  wincmd w
210  call assert_equal('two', getline(21))
211  normal 31Gdo
212  call assert_equal('three', getline(31))
213  call assert_equal('40', getline(41))
214  normal 41Gdp
215  wincmd w
216  call assert_equal('40', getline(41))
217  new
218  diffthis
219  call assert_fails('diffget', 'E101:')
220
221  windo diffoff
222  %bwipe!
223endfunc
224
225" Test putting two changes from one buffer to another
226func Test_diffput_two()
227  new a
228  let win_a = win_getid()
229  call setline(1, range(1, 10))
230  diffthis
231  new b
232  let win_b = win_getid()
233  call setline(1, range(1, 10))
234  8del
235  5del
236  diffthis
237  call win_gotoid(win_a)
238  %diffput
239  call win_gotoid(win_b)
240  call assert_equal(map(range(1, 10), 'string(v:val)'), getline(1, '$'))
241  bwipe! a
242  bwipe! b
243endfunc
244
245func Test_dp_do_buffer()
246  e! one
247  let bn1=bufnr('%')
248  let l = range(60)
249  call setline(1, l)
250  diffthis
251
252  new two
253  let l[10] = 'one'
254  let l[20] = 'two'
255  let l[30] = 'three'
256  let l[40] = 'four'
257  let l[50] = 'five'
258  call setline(1, l)
259  diffthis
260
261  " dp and do with invalid buffer number.
262  11
263  call assert_fails('norm 99999dp', 'E102:')
264  call assert_fails('norm 99999do', 'E102:')
265  call assert_fails('diffput non_existing_buffer', 'E94:')
266  call assert_fails('diffget non_existing_buffer', 'E94:')
267
268  " dp and do with valid buffer number.
269  call assert_equal('one', getline('.'))
270  exe 'norm ' . bn1 . 'do'
271  call assert_equal('10', getline('.'))
272  21
273  call assert_equal('two', getline('.'))
274  diffget one
275  call assert_equal('20', getline('.'))
276
277  31
278  exe 'norm ' . bn1 . 'dp'
279  41
280  diffput one
281  wincmd w
282  31
283  call assert_equal('three', getline('.'))
284  41
285  call assert_equal('four', getline('.'))
286
287  " dp and do with buffer number which is not in diff mode.
288  new not_in_diff_mode
289  let bn3=bufnr('%')
290  wincmd w
291  51
292  call assert_fails('exe "norm" . bn3 . "dp"', 'E103:')
293  call assert_fails('exe "norm" . bn3 . "do"', 'E103:')
294  call assert_fails('diffput not_in_diff_mode', 'E94:')
295  call assert_fails('diffget not_in_diff_mode', 'E94:')
296
297  windo diffoff
298  %bwipe!
299endfunc
300
301func Test_do_lastline()
302  e! one
303  call setline(1, ['1','2','3','4','5','6'])
304  diffthis
305
306  new two
307  call setline(1, ['2','4','5'])
308  diffthis
309
310  1
311  norm dp]c
312  norm dp]c
313  wincmd w
314  call assert_equal(4, line('$'))
315  norm G
316  norm do
317  call assert_equal(3, line('$'))
318
319  windo diffoff
320  %bwipe!
321endfunc
322
323func Test_diffoff()
324  enew!
325  call setline(1, ['Two', 'Three'])
326  redraw
327  let normattr = screenattr(1, 1)
328  diffthis
329  botright vert new
330  call setline(1, ['One', '', 'Two', 'Three'])
331  diffthis
332  redraw
333  call assert_notequal(normattr, 1->screenattr(1))
334  diffoff!
335  redraw
336  call assert_equal(normattr, screenattr(1, 1))
337  bwipe!
338  bwipe!
339endfunc
340
341func Common_icase_test()
342  edit one
343  call setline(1, ['One', 'Two', 'Three', 'Four', 'Fi#ve'])
344  redraw
345  let normattr = screenattr(1, 1)
346  diffthis
347
348  botright vert new two
349  call setline(1, ['one', 'TWO', 'Three ', 'Four', 'fI=VE'])
350  diffthis
351
352  redraw
353  call assert_equal(normattr, screenattr(1, 1))
354  call assert_equal(normattr, screenattr(2, 1))
355  call assert_notequal(normattr, screenattr(3, 1))
356  call assert_equal(normattr, screenattr(4, 1))
357
358  let dtextattr = screenattr(5, 3)
359  call assert_notequal(dtextattr, screenattr(5, 1))
360  call assert_notequal(dtextattr, screenattr(5, 5))
361
362  diffoff!
363  %bwipe!
364endfunc
365
366func Test_diffopt_icase()
367  set diffopt=icase,foldcolumn:0
368  call Common_icase_test()
369  set diffopt&
370endfunc
371
372func Test_diffopt_icase_internal()
373  set diffopt=icase,foldcolumn:0,internal
374  call Common_icase_test()
375  set diffopt&
376endfunc
377
378func Common_iwhite_test()
379  edit one
380  " Difference in trailing spaces and amount of spaces should be ignored,
381  " but not other space differences.
382  call setline(1, ["One \t", 'Two', 'Three', 'one two', 'one two', 'Four'])
383  redraw
384  let normattr = screenattr(1, 1)
385  diffthis
386
387  botright vert new two
388  call setline(1, ["One\t ", "Two\t ", 'Three', 'one   two', 'onetwo', ' Four'])
389  diffthis
390
391  redraw
392  call assert_equal(normattr, screenattr(1, 1))
393  call assert_equal(normattr, screenattr(2, 1))
394  call assert_equal(normattr, screenattr(3, 1))
395  call assert_equal(normattr, screenattr(4, 1))
396  call assert_notequal(normattr, screenattr(5, 1))
397  call assert_notequal(normattr, screenattr(6, 1))
398
399  diffoff!
400  %bwipe!
401endfunc
402
403func Test_diffopt_iwhite()
404  set diffopt=iwhite,foldcolumn:0
405  call Common_iwhite_test()
406  set diffopt&
407endfunc
408
409func Test_diffopt_iwhite_internal()
410  set diffopt=internal,iwhite,foldcolumn:0
411  call Common_iwhite_test()
412  set diffopt&
413endfunc
414
415func Test_diffopt_context()
416  enew!
417  call setline(1, ['1', '2', '3', '4', '5', '6', '7'])
418  diffthis
419  new
420  call setline(1, ['1', '2', '3', '4', '5x', '6', '7'])
421  diffthis
422
423  set diffopt=context:2
424  call assert_equal('+--  2 lines: 1', foldtextresult(1))
425  set diffopt=internal,context:2
426  call assert_equal('+--  2 lines: 1', foldtextresult(1))
427
428  set diffopt=context:1
429  call assert_equal('+--  3 lines: 1', foldtextresult(1))
430  set diffopt=internal,context:1
431  call assert_equal('+--  3 lines: 1', foldtextresult(1))
432
433  diffoff!
434  %bwipe!
435  set diffopt&
436endfunc
437
438func Test_diffopt_horizontal()
439  set diffopt=internal,horizontal
440  diffsplit
441
442  call assert_equal(&columns, winwidth(1))
443  call assert_equal(&columns, winwidth(2))
444  call assert_equal(&lines, winheight(1) + winheight(2) + 3)
445  call assert_inrange(0, 1, winheight(1) - winheight(2))
446
447  set diffopt&
448  diffoff!
449  %bwipe
450endfunc
451
452func Test_diffopt_vertical()
453  set diffopt=internal,vertical
454  diffsplit
455
456  call assert_equal(&lines - 2, winheight(1))
457  call assert_equal(&lines - 2, winheight(2))
458  call assert_equal(&columns, winwidth(1) + winwidth(2) + 1)
459  call assert_inrange(0, 1, winwidth(1) - winwidth(2))
460
461  set diffopt&
462  diffoff!
463  %bwipe
464endfunc
465
466func Test_diffopt_hiddenoff()
467  set diffopt=internal,filler,foldcolumn:0,hiddenoff
468  e! one
469  call setline(1, ['Two', 'Three'])
470  redraw
471  let normattr = screenattr(1, 1)
472  diffthis
473  botright vert new two
474  call setline(1, ['One', 'Four'])
475  diffthis
476  redraw
477  call assert_notequal(normattr, screenattr(1, 1))
478  set hidden
479  close
480  redraw
481  " should not diffing with hidden buffer two while 'hiddenoff' is enabled
482  call assert_equal(normattr, screenattr(1, 1))
483
484  bwipe!
485  bwipe!
486  set hidden& diffopt&
487endfunc
488
489func Test_diffoff_hidden()
490  set diffopt=internal,filler,foldcolumn:0
491  e! one
492  call setline(1, ['Two', 'Three'])
493  redraw
494  let normattr = screenattr(1, 1)
495  diffthis
496  botright vert new two
497  call setline(1, ['One', 'Four'])
498  diffthis
499  redraw
500  call assert_notequal(normattr, screenattr(1, 1))
501  set hidden
502  close
503  redraw
504  " diffing with hidden buffer two
505  call assert_notequal(normattr, screenattr(1, 1))
506  diffoff
507  redraw
508  call assert_equal(normattr, screenattr(1, 1))
509  diffthis
510  redraw
511  " still diffing with hidden buffer two
512  call assert_notequal(normattr, screenattr(1, 1))
513  diffoff!
514  redraw
515  call assert_equal(normattr, screenattr(1, 1))
516  diffthis
517  redraw
518  " no longer diffing with hidden buffer two
519  call assert_equal(normattr, screenattr(1, 1))
520
521  bwipe!
522  bwipe!
523  set hidden& diffopt&
524endfunc
525
526func Test_setting_cursor()
527  new Xtest1
528  put =range(1,90)
529  wq
530  new Xtest2
531  put =range(1,100)
532  wq
533
534  tabe Xtest2
535  $
536  diffsp Xtest1
537  tabclose
538
539  call delete('Xtest1')
540  call delete('Xtest2')
541endfunc
542
543func Test_diff_move_to()
544  new
545  call setline(1, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
546  diffthis
547  vnew
548  call setline(1, [1, '2x', 3, 4, 4, 5, '6x', 7, '8x', 9, '10x'])
549  diffthis
550  norm ]c
551  call assert_equal(2, line('.'))
552  norm 3]c
553  call assert_equal(9, line('.'))
554  norm 10]c
555  call assert_equal(11, line('.'))
556  norm [c
557  call assert_equal(9, line('.'))
558  norm 2[c
559  call assert_equal(5, line('.'))
560  norm 10[c
561  call assert_equal(2, line('.'))
562  %bwipe!
563endfunc
564
565func Test_diffexpr()
566  if !executable('diff')
567    return
568  endif
569
570  func DiffExpr()
571    " Prepent some text to check diff type detection
572    call writefile(['warning', '  message'], v:fname_out)
573    silent exe '!diff ' . v:fname_in . ' ' . v:fname_new . '>>' . v:fname_out
574  endfunc
575  set diffexpr=DiffExpr()
576  set diffopt=foldcolumn:0
577
578  enew!
579  call setline(1, ['one', 'two', 'three'])
580  redraw
581  let normattr = screenattr(1, 1)
582  diffthis
583
584  botright vert new
585  call setline(1, ['one', 'two', 'three.'])
586  diffthis
587
588  redraw
589  call assert_equal(normattr, screenattr(1, 1))
590  call assert_equal(normattr, screenattr(2, 1))
591  call assert_notequal(normattr, screenattr(3, 1))
592
593  diffoff!
594  %bwipe!
595  set diffexpr& diffopt&
596endfunc
597
598func Test_diffpatch()
599  " The patch program on MS-Windows may fail or hang.
600  if !executable('patch') || !has('unix')
601    return
602  endif
603  new
604  insert
605***************
606*** 1,3 ****
607  1
608! 2
609  3
610--- 1,4 ----
611  1
612! 2x
613  3
614+ 4
615.
616  saveas! Xpatch
617  bwipe!
618  new
619  call assert_fails('diffpatch Xpatch', 'E816:')
620
621  for name in ['Xpatch', 'Xpatch$HOME', 'Xpa''tch']
622    call setline(1, ['1', '2', '3'])
623    if name != 'Xpatch'
624      call rename('Xpatch', name)
625    endif
626    exe 'diffpatch ' . escape(name, '$')
627    call assert_equal(['1', '2x', '3', '4'], getline(1, '$'))
628    if name != 'Xpatch'
629      call rename(name, 'Xpatch')
630    endif
631    bwipe!
632  endfor
633
634  call delete('Xpatch')
635  bwipe!
636endfunc
637
638func Test_diff_too_many_buffers()
639  for i in range(1, 8)
640    exe "new Xtest" . i
641    diffthis
642  endfor
643  new Xtest9
644  call assert_fails('diffthis', 'E96:')
645  %bwipe!
646endfunc
647
648func Test_diff_nomodifiable()
649  new
650  call setline(1, [1, 2, 3, 4])
651  setl nomodifiable
652  diffthis
653  vnew
654  call setline(1, ['1x', 2, 3, 3, 4])
655  diffthis
656  call assert_fails('norm dp', 'E793:')
657  setl nomodifiable
658  call assert_fails('norm do', 'E21:')
659  %bwipe!
660endfunc
661
662func Test_diff_hlID()
663  new
664  call setline(1, [1, 2, 3])
665  diffthis
666  vnew
667  call setline(1, ['1x', 2, 'x', 3])
668  diffthis
669  redraw
670
671  call diff_hlID(-1, 1)->synIDattr("name")->assert_equal("")
672
673  call diff_hlID(1, 1)->synIDattr("name")->assert_equal("DiffChange")
674  call diff_hlID(1, 2)->synIDattr("name")->assert_equal("DiffText")
675  call diff_hlID(2, 1)->synIDattr("name")->assert_equal("")
676  call diff_hlID(3, 1)->synIDattr("name")->assert_equal("DiffAdd")
677  eval 4->diff_hlID(1)->synIDattr("name")->assert_equal("")
678
679  wincmd w
680  call assert_equal(synIDattr(diff_hlID(1, 1), "name"), "DiffChange")
681  call assert_equal(synIDattr(diff_hlID(2, 1), "name"), "")
682  call assert_equal(synIDattr(diff_hlID(3, 1), "name"), "")
683
684  %bwipe!
685endfunc
686
687func Test_diff_filler()
688  new
689  call setline(1, [1, 2, 3, 'x', 4])
690  diffthis
691  vnew
692  call setline(1, [1, 2, 'y', 'y', 3, 4])
693  diffthis
694  redraw
695
696  call assert_equal([0, 0, 0, 0, 0, 0, 0, 1, 0], map(range(-1, 7), 'v:val->diff_filler()'))
697  wincmd w
698  call assert_equal([0, 0, 0, 0, 2, 0, 0, 0], map(range(-1, 6), 'diff_filler(v:val)'))
699
700  %bwipe!
701endfunc
702
703func Test_diff_lastline()
704  enew!
705  only!
706  call setline(1, ['This is a ', 'line with five ', 'rows'])
707  diffthis
708  botright vert new
709  call setline(1, ['This is', 'a line with ', 'four rows'])
710  diffthis
711  1
712  call feedkeys("Je a\<CR>", 'tx')
713  call feedkeys("Je a\<CR>", 'tx')
714  let w1lines = winline()
715  wincmd w
716  $
717  let w2lines = winline()
718  call assert_equal(w2lines, w1lines)
719  bwipe!
720  bwipe!
721endfunc
722
723func WriteDiffFiles(buf, list1, list2)
724  call writefile(a:list1, 'Xfile1')
725  call writefile(a:list2, 'Xfile2')
726  if a:buf
727    call term_sendkeys(a:buf, ":checktime\<CR>")
728  endif
729endfunc
730
731" Verify a screendump with both the internal and external diff.
732func VerifyBoth(buf, dumpfile, extra)
733  " trailing : for leaving the cursor on the command line
734  for cmd in [":set diffopt=filler" . a:extra . "\<CR>:", ":set diffopt+=internal\<CR>:"]
735    call term_sendkeys(a:buf, cmd)
736    if VerifyScreenDump(a:buf, a:dumpfile, {}, cmd =~ 'internal' ? 'internal' : 'external')
737      break " don't let the next iteration overwrite the "failed" file.
738    endif
739  endfor
740endfunc
741
742" Verify a screendump with the internal diff only.
743func VerifyInternal(buf, dumpfile, extra)
744  call term_sendkeys(a:buf, ":diffupdate!\<CR>")
745  " trailing : for leaving the cursor on the command line
746  call term_sendkeys(a:buf, ":set diffopt=internal,filler" . a:extra . "\<CR>:")
747  call term_wait(a:buf)
748  call VerifyScreenDump(a:buf, a:dumpfile, {})
749endfunc
750
751func Test_diff_screen()
752  CheckScreendump
753  CheckFeature menu
754
755  " clean up already existing swap files, just in case
756  call delete('.Xfile1.swp')
757  call delete('.Xfile2.swp')
758
759  " Test 1: Add a line in beginning of file 2
760  call WriteDiffFiles(0, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
761  let buf = RunVimInTerminal('-d Xfile1 Xfile2', {})
762  " Set autoread mode, so that Vim won't complain once we re-write the test
763  " files
764  call term_sendkeys(buf, ":set autoread\<CR>\<c-w>w:set autoread\<CR>\<c-w>w")
765
766  call VerifyBoth(buf, 'Test_diff_01', '')
767
768  " Test 2: Add a line in beginning of file 1
769  call WriteDiffFiles(buf, [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
770  call VerifyBoth(buf, 'Test_diff_02', '')
771
772  " Test 3: Add a line at the end of file 2
773  call WriteDiffFiles(buf, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11])
774  call VerifyBoth(buf, 'Test_diff_03', '')
775
776  " Test 4: Add a line at the end of file 1
777  call WriteDiffFiles(buf, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
778  call VerifyBoth(buf, 'Test_diff_04', '')
779
780  " Test 5: Add a line in the middle of file 2, remove on at the end of file 1
781  call WriteDiffFiles(buf, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11], [1, 2, 3, 4, 4, 5, 6, 7, 8, 9, 10])
782  call VerifyBoth(buf, 'Test_diff_05', '')
783
784  " Test 6: Add a line in the middle of file 1, remove on at the end of file 2
785  call WriteDiffFiles(buf, [1, 2, 3, 4, 4, 5, 6, 7, 8, 9, 10], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11])
786  call VerifyBoth(buf, 'Test_diff_06', '')
787
788  " Variants on test 6 with different context settings
789  call term_sendkeys(buf, ":set diffopt+=context:2\<cr>")
790  call VerifyScreenDump(buf, 'Test_diff_06.2', {})
791  call term_sendkeys(buf, ":set diffopt-=context:2\<cr>")
792  call term_sendkeys(buf, ":set diffopt+=context:1\<cr>")
793  call VerifyScreenDump(buf, 'Test_diff_06.1', {})
794  call term_sendkeys(buf, ":set diffopt-=context:1\<cr>")
795  call term_sendkeys(buf, ":set diffopt+=context:0\<cr>")
796  call VerifyScreenDump(buf, 'Test_diff_06.0', {})
797  call term_sendkeys(buf, ":set diffopt-=context:0\<cr>")
798
799  " Test 7 - 9: Test normal/patience/histogram diff algorithm
800  call WriteDiffFiles(buf, ['#include <stdio.h>', '', '// Frobs foo heartily', 'int frobnitz(int foo)', '{',
801      \ '    int i;', '    for(i = 0; i < 10; i++)', '    {', '        printf("Your answer is: ");',
802      \ '        printf("%d\n", foo);', '    }', '}', '', 'int fact(int n)', '{', '    if(n > 1)', '    {',
803      \ '        return fact(n-1) * n;', '    }', '    return 1;', '}', '', 'int main(int argc, char **argv)',
804      \ '{', '    frobnitz(fact(10));', '}'],
805      \ ['#include <stdio.h>', '', 'int fib(int n)', '{', '    if(n > 2)', '    {',
806      \ '        return fib(n-1) + fib(n-2);', '    }', '    return 1;', '}', '', '// Frobs foo heartily',
807      \ 'int frobnitz(int foo)', '{', '    int i;', '    for(i = 0; i < 10; i++)', '    {',
808      \ '        printf("%d\n", foo);', '    }', '}', '',
809      \ 'int main(int argc, char **argv)', '{', '    frobnitz(fib(10));', '}'])
810  call term_sendkeys(buf, ":diffupdate!\<cr>")
811  call term_sendkeys(buf, ":set diffopt+=internal\<cr>")
812  call VerifyScreenDump(buf, 'Test_diff_07', {})
813
814  call term_sendkeys(buf, ":set diffopt+=algorithm:patience\<cr>")
815  call VerifyScreenDump(buf, 'Test_diff_08', {})
816
817  call term_sendkeys(buf, ":set diffopt+=algorithm:histogram\<cr>")
818  call VerifyScreenDump(buf, 'Test_diff_09', {})
819
820  " Test 10-11: normal/indent-heuristic
821  call term_sendkeys(buf, ":set diffopt&vim\<cr>")
822  call WriteDiffFiles(buf, ['', '  def finalize(values)', '', '    values.each do |v|', '      v.finalize', '    end'],
823      \ ['', '  def finalize(values)', '', '    values.each do |v|', '      v.prepare', '    end', '',
824      \ '    values.each do |v|', '      v.finalize', '    end'])
825  call term_sendkeys(buf, ":diffupdate!\<cr>")
826  call term_sendkeys(buf, ":set diffopt+=internal\<cr>")
827  call VerifyScreenDump(buf, 'Test_diff_10', {})
828
829  " Leave trailing : at commandline!
830  call term_sendkeys(buf, ":set diffopt+=indent-heuristic\<cr>:\<cr>")
831  call VerifyScreenDump(buf, 'Test_diff_11', {}, 'one')
832  " shouldn't matter, if indent-algorithm comes before or after the algorithm
833  call term_sendkeys(buf, ":set diffopt&\<cr>")
834  call term_sendkeys(buf, ":set diffopt+=indent-heuristic,algorithm:patience\<cr>:\<cr>")
835  call VerifyScreenDump(buf, 'Test_diff_11', {}, 'two')
836  call term_sendkeys(buf, ":set diffopt&\<cr>")
837  call term_sendkeys(buf, ":set diffopt+=algorithm:patience,indent-heuristic\<cr>:\<cr>")
838  call VerifyScreenDump(buf, 'Test_diff_11', {}, 'three')
839
840  " Test 12: diff the same file
841  call WriteDiffFiles(buf, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
842  call VerifyBoth(buf, 'Test_diff_12', '')
843
844  " Test 13: diff an empty file
845  call WriteDiffFiles(buf, [], [])
846  call VerifyBoth(buf, 'Test_diff_13', '')
847
848  " Test 14: test diffopt+=icase
849  call WriteDiffFiles(buf, ['a', 'b', 'cd'], ['A', 'b', 'cDe'])
850  call VerifyBoth(buf, 'Test_diff_14', " diffopt+=filler diffopt+=icase")
851
852  " Test 15-16: test diffopt+=iwhite
853  call WriteDiffFiles(buf, ['int main()', '{', '   printf("Hello, World!");', '   return 0;', '}'],
854      \ ['int main()', '{', '   if (0)', '   {', '      printf("Hello, World!");', '      return 0;', '   }', '}'])
855  call term_sendkeys(buf, ":diffupdate!\<cr>")
856  call term_sendkeys(buf, ":set diffopt&vim diffopt+=filler diffopt+=iwhite\<cr>")
857  call VerifyScreenDump(buf, 'Test_diff_15', {})
858  call term_sendkeys(buf, ":set diffopt+=internal\<cr>")
859  call VerifyScreenDump(buf, 'Test_diff_16', {})
860
861  " Test 17: test diffopt+=iblank
862  call WriteDiffFiles(buf, ['a', ' ', 'cd', 'ef', 'xxx'], ['a', 'cd', '', 'ef', 'yyy'])
863  call VerifyInternal(buf, 'Test_diff_17', " diffopt+=iblank")
864
865  " Test 18: test diffopt+=iblank,iwhite / iwhiteall / iwhiteeol
866  call VerifyInternal(buf, 'Test_diff_18', " diffopt+=iblank,iwhite")
867  call VerifyInternal(buf, 'Test_diff_18', " diffopt+=iblank,iwhiteall")
868  call VerifyInternal(buf, 'Test_diff_18', " diffopt+=iblank,iwhiteeol")
869
870  " Test 19: test diffopt+=iwhiteeol
871  call WriteDiffFiles(buf, ['a ', 'x', 'cd', 'ef', 'xx  xx', 'foo', 'bar'], ['a', 'x', 'c d', ' ef', 'xx xx', 'foo', '', 'bar'])
872  call VerifyInternal(buf, 'Test_diff_19', " diffopt+=iwhiteeol")
873
874  " Test 19: test diffopt+=iwhiteall
875  call VerifyInternal(buf, 'Test_diff_20', " diffopt+=iwhiteall")
876
877  " clean up
878  call StopVimInTerminal(buf)
879  call delete('Xfile1')
880  call delete('Xfile2')
881endfunc
882
883func Test_diff_with_cursorline()
884  CheckScreendump
885
886  call writefile([
887	\ 'hi CursorLine ctermbg=red ctermfg=white',
888	\ 'set cursorline',
889	\ 'call setline(1, ["foo","foo","foo","bar"])',
890	\ 'vnew',
891	\ 'call setline(1, ["bee","foo","foo","baz"])',
892	\ 'windo diffthis',
893	\ '2wincmd w',
894	\ ], 'Xtest_diff_cursorline')
895  let buf = RunVimInTerminal('-S Xtest_diff_cursorline', {})
896
897  call VerifyScreenDump(buf, 'Test_diff_with_cursorline_01', {})
898  call term_sendkeys(buf, "j")
899  call VerifyScreenDump(buf, 'Test_diff_with_cursorline_02', {})
900  call term_sendkeys(buf, "j")
901  call VerifyScreenDump(buf, 'Test_diff_with_cursorline_03', {})
902
903  " clean up
904  call StopVimInTerminal(buf)
905  call delete('Xtest_diff_cursorline')
906endfunc
907
908func Test_diff_with_syntax()
909  CheckScreendump
910
911  let lines =<< trim END
912  	void doNothing() {
913	   int x = 0;
914	   char *s = "hello";
915	   return 5;
916	}
917  END
918  call writefile(lines, 'Xprogram1.c')
919  let lines =<< trim END
920  	void doSomething() {
921	   int x = 0;
922	   char *s = "there";
923	   return 5;
924	}
925  END
926  call writefile(lines, 'Xprogram2.c')
927
928  let lines =<< trim END
929  	edit Xprogram1.c
930	diffsplit Xprogram2.c
931  END
932  call writefile(lines, 'Xtest_diff_syntax')
933  let buf = RunVimInTerminal('-S Xtest_diff_syntax', {})
934
935  call VerifyScreenDump(buf, 'Test_diff_syntax_1', {})
936
937  " clean up
938  call StopVimInTerminal(buf)
939  call delete('Xtest_diff_syntax')
940  call delete('Xprogram1.c')
941  call delete('Xprogram2.c')
942endfunc
943
944func Test_diff_of_diff()
945  CheckScreendump
946  CheckFeature rightleft
947
948  call writefile([
949	\ 'call setline(1, ["aa","bb","cc","@@ -3,2 +5,7 @@","dd","ee","ff"])',
950	\ 'vnew',
951	\ 'call setline(1, ["aa","bb","cc"])',
952	\ 'windo diffthis',
953	\ '1wincmd w',
954	\ 'setlocal number',
955	\ ], 'Xtest_diff_diff')
956  let buf = RunVimInTerminal('-S Xtest_diff_diff', {})
957
958  call VerifyScreenDump(buf, 'Test_diff_of_diff_01', {})
959
960  call term_sendkeys(buf, ":set rightleft\<cr>")
961  call VerifyScreenDump(buf, 'Test_diff_of_diff_02', {})
962
963  " clean up
964  call StopVimInTerminal(buf)
965  call delete('Xtest_diff_diff')
966endfunc
967
968func CloseoffSetup()
969  enew
970  call setline(1, ['one', 'two', 'three'])
971  diffthis
972  new
973  call setline(1, ['one', 'tow', 'three'])
974  diffthis
975  call assert_equal(1, &diff)
976  only!
977endfunc
978
979func Test_diff_closeoff()
980  " "closeoff" included by default: last diff win gets 'diff' reset'
981  call CloseoffSetup()
982  call assert_equal(0, &diff)
983  enew!
984
985  " "closeoff" excluded: last diff win keeps 'diff' set'
986  set diffopt-=closeoff
987  call CloseoffSetup()
988  call assert_equal(1, &diff)
989  diffoff!
990  enew!
991endfunc
992
993func Test_diff_maintains_change_mark()
994  enew!
995  call setline(1, ['a', 'b', 'c', 'd'])
996  diffthis
997  new
998  call setline(1, ['a', 'b', 'c', 'e'])
999  " Set '[ and '] marks
1000  2,3yank
1001  call assert_equal([2, 3], [line("'["), line("']")])
1002  " Verify they aren't affected by the implicit diff
1003  diffthis
1004  call assert_equal([2, 3], [line("'["), line("']")])
1005  " Verify they aren't affected by an explicit diff
1006  diffupdate
1007  call assert_equal([2, 3], [line("'["), line("']")])
1008  bwipe!
1009  bwipe!
1010endfunc
1011