1" Tests for diff mode
2
3source shared.vim
4source screendump.vim
5source check.vim
6
7func Test_diff_fold_sync()
8  enew!
9  let g:update_count = 0
10  au DiffUpdated * let g:update_count += 1
11
12  let l = range(50)
13  call setline(1, l)
14  diffthis
15  let winone = win_getid()
16  new
17  let l[25] = 'diff'
18  call setline(1, l)
19  diffthis
20  let wintwo = win_getid()
21  " line 15 is inside the closed fold
22  call assert_equal(19, foldclosedend(10))
23  call win_gotoid(winone)
24  call assert_equal(19, foldclosedend(10))
25  " open the fold
26  normal zv
27  call assert_equal(-1, foldclosedend(10))
28  " fold in other window must have opened too
29  call win_gotoid(wintwo)
30  call assert_equal(-1, foldclosedend(10))
31
32  " cursor position is in sync
33  normal 23G
34  call win_gotoid(winone)
35  call assert_equal(23, getcurpos()[1])
36
37  call assert_equal(1, g:update_count)
38  au! DiffUpdated
39
40  windo diffoff
41  close!
42  set nomodified
43endfunc
44
45func Test_vert_split()
46  set diffopt=filler
47  call Common_vert_split()
48  set diffopt&
49endfunc
50
51func Test_vert_split_internal()
52  set diffopt=internal,filler
53  call Common_vert_split()
54  set diffopt&
55endfunc
56
57func Common_vert_split()
58  " Disable the title to avoid xterm keeping the wrong one.
59  set notitle noicon
60  new
61  let l = ['1 aa', '2 bb', '3 cc', '4 dd', '5 ee']
62  call setline(1, l)
63  w! Xtest
64  normal dd
65  $
66  put
67  normal kkrXoxxx
68  w! Xtest2
69  file Nop
70  normal ggoyyyjjjozzzz
71  set foldmethod=marker foldcolumn=4
72  call assert_equal(0, &diff)
73  call assert_equal('marker', &foldmethod)
74  call assert_equal(4, &foldcolumn)
75  call assert_equal(0, &scrollbind)
76  call assert_equal(0, &cursorbind)
77  call assert_equal(1, &wrap)
78
79  vert diffsplit Xtest
80  vert diffsplit Xtest2
81  call assert_equal(1, &diff)
82  call assert_equal('diff', &foldmethod)
83  call assert_equal(2, &foldcolumn)
84  call assert_equal(1, &scrollbind)
85  call assert_equal(1, &cursorbind)
86  call assert_equal(0, &wrap)
87
88  let diff_fdm = &fdm
89  let diff_fdc = &fdc
90  " repeat entering diff mode here to see if this saves the wrong settings
91  diffthis
92  " jump to second window for a moment to have filler line appear at start of
93  " first window
94  wincmd w
95  normal gg
96  wincmd p
97  normal gg
98  call assert_equal(2, winline())
99  normal j
100  call assert_equal(4, winline())
101  normal j
102  call assert_equal(5, winline())
103  normal j
104  call assert_equal(6, winline())
105  normal j
106  call assert_equal(8, winline())
107  normal j
108  call assert_equal(9, winline())
109
110  wincmd w
111  normal gg
112  call assert_equal(1, winline())
113  normal j
114  call assert_equal(2, winline())
115  normal j
116  call assert_equal(4, winline())
117  normal j
118  call assert_equal(5, winline())
119  normal j
120  call assert_equal(8, winline())
121
122  wincmd w
123  normal gg
124  call assert_equal(2, winline())
125  normal j
126  call assert_equal(3, winline())
127  normal j
128  call assert_equal(4, winline())
129  normal j
130  call assert_equal(5, winline())
131  normal j
132  call assert_equal(6, winline())
133  normal j
134  call assert_equal(7, winline())
135  normal j
136  call assert_equal(8, winline())
137
138  " Test diffoff
139  diffoff!
140  1wincmd 2
141  let &diff = 1
142  let &fdm = diff_fdm
143  let &fdc = diff_fdc
144  4wincmd w
145  diffoff!
146  1wincmd w
147  call assert_equal(0, &diff)
148  call assert_equal('marker', &foldmethod)
149  call assert_equal(4, &foldcolumn)
150  call assert_equal(0, &scrollbind)
151  call assert_equal(0, &cursorbind)
152  call assert_equal(1, &wrap)
153
154  wincmd w
155  call assert_equal(0, &diff)
156  call assert_equal('marker', &foldmethod)
157  call assert_equal(4, &foldcolumn)
158  call assert_equal(0, &scrollbind)
159  call assert_equal(0, &cursorbind)
160  call assert_equal(1, &wrap)
161
162  wincmd w
163  call assert_equal(0, &diff)
164  call assert_equal('marker', &foldmethod)
165  call assert_equal(4, &foldcolumn)
166  call assert_equal(0, &scrollbind)
167  call assert_equal(0, &cursorbind)
168  call assert_equal(1, &wrap)
169
170  call delete('Xtest')
171  call delete('Xtest2')
172  windo bw!
173endfunc
174
175func Test_filler_lines()
176  " Test that diffing shows correct filler lines
177  enew!
178  put =range(4,10)
179  1d _
180  vnew
181  put =range(1,10)
182  1d _
183  windo diffthis
184  wincmd h
185  call assert_equal(1, line('w0'))
186  unlet! diff_fdm diff_fdc
187  windo diffoff
188  bwipe!
189  enew!
190endfunc
191
192func Test_diffget_diffput()
193  enew!
194  let l = range(50)
195  call setline(1, l)
196  call assert_fails('diffget', 'E99:')
197  diffthis
198  call assert_fails('diffget', 'E100:')
199  new
200  let l[10] = 'one'
201  let l[20] = 'two'
202  let l[30] = 'three'
203  let l[40] = 'four'
204  call setline(1, l)
205  diffthis
206  call assert_equal('one', getline(11))
207  11diffget
208  call assert_equal('10', getline(11))
209  21diffput
210  wincmd w
211  call assert_equal('two', getline(21))
212  normal 31Gdo
213  call assert_equal('three', getline(31))
214  call assert_equal('40', getline(41))
215  normal 41Gdp
216  wincmd w
217  call assert_equal('40', getline(41))
218  new
219  diffthis
220  call assert_fails('diffget', 'E101:')
221
222  windo diffoff
223  %bwipe!
224endfunc
225
226" Test putting two changes from one buffer to another
227func Test_diffput_two()
228  new a
229  let win_a = win_getid()
230  call setline(1, range(1, 10))
231  diffthis
232  new b
233  let win_b = win_getid()
234  call setline(1, range(1, 10))
235  8del
236  5del
237  diffthis
238  call win_gotoid(win_a)
239  %diffput
240  call win_gotoid(win_b)
241  call assert_equal(map(range(1, 10), 'string(v:val)'), getline(1, '$'))
242  bwipe! a
243  bwipe! b
244endfunc
245
246" Test for :diffget/:diffput with a range that is inside a diff chunk
247func Test_diffget_diffput_range()
248  call setline(1, range(1, 10))
249  new
250  call setline(1, range(11, 20))
251  windo diffthis
252  3,5diffget
253  call assert_equal(['13', '14', '15'], getline(3, 5))
254  call setline(1, range(1, 10))
255  4,8diffput
256  wincmd p
257  call assert_equal(['13', '4', '5', '6', '7', '8', '19'], getline(3, 9))
258  %bw!
259endfunc
260
261" Test for :diffget/:diffput with an empty buffer and a non-empty buffer
262func Test_diffget_diffput_empty_buffer()
263  %d _
264  new
265  call setline(1, 'one')
266  windo diffthis
267  diffget
268  call assert_equal(['one'], getline(1, '$'))
269  %d _
270  diffput
271  wincmd p
272  call assert_equal([''], getline(1, '$'))
273  %bw!
274endfunc
275
276" :diffput and :diffget completes names of buffers which
277" are in diff mode and which are different then current buffer.
278" No completion when the current window is not in diff mode.
279func Test_diffget_diffput_completion()
280  e            Xdiff1 | diffthis
281  botright new Xdiff2
282  botright new Xdiff3 | split | diffthis
283  botright new Xdiff4 | diffthis
284
285  wincmd t
286  call assert_equal('Xdiff1', bufname('%'))
287  call feedkeys(":diffput \<C-A>\<C-B>\"\<CR>", 'tx')
288  call assert_equal('"diffput Xdiff3 Xdiff4', @:)
289  call feedkeys(":diffget \<C-A>\<C-B>\"\<CR>", 'tx')
290  call assert_equal('"diffget Xdiff3 Xdiff4', @:)
291  call assert_equal(['Xdiff3', 'Xdiff4'], getcompletion('', 'diff_buffer'))
292
293  " Xdiff2 is not in diff mode, so no completion for :diffput, :diffget
294  wincmd j
295  call assert_equal('Xdiff2', bufname('%'))
296  call feedkeys(":diffput \<C-A>\<C-B>\"\<CR>", 'tx')
297  call assert_equal('"diffput ', @:)
298  call feedkeys(":diffget \<C-A>\<C-B>\"\<CR>", 'tx')
299  call assert_equal('"diffget ', @:)
300  call assert_equal([], getcompletion('', 'diff_buffer'))
301
302  " Xdiff3 is split in 2 windows, only the top one is in diff mode.
303  " So completion of :diffput :diffget only happens in the top window.
304  wincmd j
305  call assert_equal('Xdiff3', bufname('%'))
306  call assert_equal(1, &diff)
307  call feedkeys(":diffput \<C-A>\<C-B>\"\<CR>", 'tx')
308  call assert_equal('"diffput Xdiff1 Xdiff4', @:)
309  call feedkeys(":diffget \<C-A>\<C-B>\"\<CR>", 'tx')
310  call assert_equal('"diffget Xdiff1 Xdiff4', @:)
311  call assert_equal(['Xdiff1', 'Xdiff4'], getcompletion('', 'diff_buffer'))
312
313  wincmd j
314  call assert_equal('Xdiff3', bufname('%'))
315  call assert_equal(0, &diff)
316  call feedkeys(":diffput \<C-A>\<C-B>\"\<CR>", 'tx')
317  call assert_equal('"diffput ', @:)
318  call feedkeys(":diffget \<C-A>\<C-B>\"\<CR>", 'tx')
319  call assert_equal('"diffget ', @:)
320  call assert_equal([], getcompletion('', 'diff_buffer'))
321
322  wincmd j
323  call assert_equal('Xdiff4', bufname('%'))
324  call feedkeys(":diffput \<C-A>\<C-B>\"\<CR>", 'tx')
325  call assert_equal('"diffput Xdiff1 Xdiff3', @:)
326  call feedkeys(":diffget \<C-A>\<C-B>\"\<CR>", 'tx')
327  call assert_equal('"diffget Xdiff1 Xdiff3', @:)
328  call assert_equal(['Xdiff1', 'Xdiff3'], getcompletion('', 'diff_buffer'))
329
330  %bwipe
331endfunc
332
333func Test_dp_do_buffer()
334  e! one
335  let bn1=bufnr('%')
336  let l = range(60)
337  call setline(1, l)
338  diffthis
339
340  new two
341  let l[10] = 'one'
342  let l[20] = 'two'
343  let l[30] = 'three'
344  let l[40] = 'four'
345  let l[50] = 'five'
346  call setline(1, l)
347  diffthis
348
349  " dp and do with invalid buffer number.
350  11
351  call assert_fails('norm 99999dp', 'E102:')
352  call assert_fails('norm 99999do', 'E102:')
353  call assert_fails('diffput non_existing_buffer', 'E94:')
354  call assert_fails('diffget non_existing_buffer', 'E94:')
355
356  " dp and do with valid buffer number.
357  call assert_equal('one', getline('.'))
358  exe 'norm ' . bn1 . 'do'
359  call assert_equal('10', getline('.'))
360  21
361  call assert_equal('two', getline('.'))
362  diffget one
363  call assert_equal('20', getline('.'))
364
365  31
366  exe 'norm ' . bn1 . 'dp'
367  41
368  diffput one
369  wincmd w
370  31
371  call assert_equal('three', getline('.'))
372  41
373  call assert_equal('four', getline('.'))
374
375  " dp and do with buffer number which is not in diff mode.
376  new not_in_diff_mode
377  let bn3=bufnr('%')
378  wincmd w
379  51
380  call assert_fails('exe "norm" . bn3 . "dp"', 'E103:')
381  call assert_fails('exe "norm" . bn3 . "do"', 'E103:')
382  call assert_fails('diffput not_in_diff_mode', 'E94:')
383  call assert_fails('diffget not_in_diff_mode', 'E94:')
384
385  windo diffoff
386  %bwipe!
387endfunc
388
389func Test_do_lastline()
390  e! one
391  call setline(1, ['1','2','3','4','5','6'])
392  diffthis
393
394  new two
395  call setline(1, ['2','4','5'])
396  diffthis
397
398  1
399  norm dp]c
400  norm dp]c
401  wincmd w
402  call assert_equal(4, line('$'))
403  norm G
404  norm do
405  call assert_equal(3, line('$'))
406
407  windo diffoff
408  %bwipe!
409endfunc
410
411func Test_diffoff()
412  enew!
413  call setline(1, ['Two', 'Three'])
414  redraw
415  let normattr = screenattr(1, 1)
416  diffthis
417  botright vert new
418  call setline(1, ['One', '', 'Two', 'Three'])
419  diffthis
420  redraw
421  call assert_notequal(normattr, 1->screenattr(1))
422  diffoff!
423  redraw
424  call assert_equal(normattr, screenattr(1, 1))
425  bwipe!
426  bwipe!
427endfunc
428
429func Common_icase_test()
430  edit one
431  call setline(1, ['One', 'Two', 'Three', 'Four', 'Fi#ve'])
432  redraw
433  let normattr = screenattr(1, 1)
434  diffthis
435
436  botright vert new two
437  call setline(1, ['one', 'TWO', 'Three ', 'Four', 'fI=VE'])
438  diffthis
439
440  redraw
441  call assert_equal(normattr, screenattr(1, 1))
442  call assert_equal(normattr, screenattr(2, 1))
443  call assert_notequal(normattr, screenattr(3, 1))
444  call assert_equal(normattr, screenattr(4, 1))
445
446  let dtextattr = screenattr(5, 3)
447  call assert_notequal(dtextattr, screenattr(5, 1))
448  call assert_notequal(dtextattr, screenattr(5, 5))
449
450  diffoff!
451  %bwipe!
452endfunc
453
454func Test_diffopt_icase()
455  set diffopt=icase,foldcolumn:0
456  call Common_icase_test()
457  set diffopt&
458endfunc
459
460func Test_diffopt_icase_internal()
461  set diffopt=icase,foldcolumn:0,internal
462  call Common_icase_test()
463  set diffopt&
464endfunc
465
466func Common_iwhite_test()
467  edit one
468  " Difference in trailing spaces and amount of spaces should be ignored,
469  " but not other space differences.
470  call setline(1, ["One \t", 'Two', 'Three', 'one two', 'one two', 'Four'])
471  redraw
472  let normattr = screenattr(1, 1)
473  diffthis
474
475  botright vert new two
476  call setline(1, ["One\t ", "Two\t ", 'Three', 'one   two', 'onetwo', ' Four'])
477  diffthis
478
479  redraw
480  call assert_equal(normattr, screenattr(1, 1))
481  call assert_equal(normattr, screenattr(2, 1))
482  call assert_equal(normattr, screenattr(3, 1))
483  call assert_equal(normattr, screenattr(4, 1))
484  call assert_notequal(normattr, screenattr(5, 1))
485  call assert_notequal(normattr, screenattr(6, 1))
486
487  diffoff!
488  %bwipe!
489endfunc
490
491func Test_diffopt_iwhite()
492  set diffopt=iwhite,foldcolumn:0
493  call Common_iwhite_test()
494  set diffopt&
495endfunc
496
497func Test_diffopt_iwhite_internal()
498  set diffopt=internal,iwhite,foldcolumn:0
499  call Common_iwhite_test()
500  set diffopt&
501endfunc
502
503func Test_diffopt_context()
504  enew!
505  call setline(1, ['1', '2', '3', '4', '5', '6', '7'])
506  diffthis
507  new
508  call setline(1, ['1', '2', '3', '4', '5x', '6', '7'])
509  diffthis
510
511  set diffopt=context:2
512  call assert_equal('+--  2 lines: 1', foldtextresult(1))
513  set diffopt=internal,context:2
514  call assert_equal('+--  2 lines: 1', foldtextresult(1))
515
516  set diffopt=context:1
517  call assert_equal('+--  3 lines: 1', foldtextresult(1))
518  set diffopt=internal,context:1
519  call assert_equal('+--  3 lines: 1', foldtextresult(1))
520
521  diffoff!
522  %bwipe!
523  set diffopt&
524endfunc
525
526func Test_diffopt_horizontal()
527  set diffopt=internal,horizontal
528  diffsplit
529
530  call assert_equal(&columns, winwidth(1))
531  call assert_equal(&columns, winwidth(2))
532  call assert_equal(&lines, winheight(1) + winheight(2) + 3)
533  call assert_inrange(0, 1, winheight(1) - winheight(2))
534
535  set diffopt&
536  diffoff!
537  %bwipe
538endfunc
539
540func Test_diffopt_vertical()
541  set diffopt=internal,vertical
542  diffsplit
543
544  call assert_equal(&lines - 2, winheight(1))
545  call assert_equal(&lines - 2, winheight(2))
546  call assert_equal(&columns, winwidth(1) + winwidth(2) + 1)
547  call assert_inrange(0, 1, winwidth(1) - winwidth(2))
548
549  set diffopt&
550  diffoff!
551  %bwipe
552endfunc
553
554func Test_diffopt_hiddenoff()
555  set diffopt=internal,filler,foldcolumn:0,hiddenoff
556  e! one
557  call setline(1, ['Two', 'Three'])
558  redraw
559  let normattr = screenattr(1, 1)
560  diffthis
561  botright vert new two
562  call setline(1, ['One', 'Four'])
563  diffthis
564  redraw
565  call assert_notequal(normattr, screenattr(1, 1))
566  set hidden
567  close
568  redraw
569  " should not diffing with hidden buffer two while 'hiddenoff' is enabled
570  call assert_equal(normattr, screenattr(1, 1))
571
572  bwipe!
573  bwipe!
574  set hidden& diffopt&
575endfunc
576
577func Test_diffoff_hidden()
578  set diffopt=internal,filler,foldcolumn:0
579  e! one
580  call setline(1, ['Two', 'Three'])
581  redraw
582  let normattr = screenattr(1, 1)
583  diffthis
584  botright vert new two
585  call setline(1, ['One', 'Four'])
586  diffthis
587  redraw
588  call assert_notequal(normattr, screenattr(1, 1))
589  set hidden
590  close
591  redraw
592  " diffing with hidden buffer two
593  call assert_notequal(normattr, screenattr(1, 1))
594  diffoff
595  redraw
596  call assert_equal(normattr, screenattr(1, 1))
597  diffthis
598  redraw
599  " still diffing with hidden buffer two
600  call assert_notequal(normattr, screenattr(1, 1))
601  diffoff!
602  redraw
603  call assert_equal(normattr, screenattr(1, 1))
604  diffthis
605  redraw
606  " no longer diffing with hidden buffer two
607  call assert_equal(normattr, screenattr(1, 1))
608
609  bwipe!
610  bwipe!
611  set hidden& diffopt&
612endfunc
613
614func Test_setting_cursor()
615  new Xtest1
616  put =range(1,90)
617  wq
618  new Xtest2
619  put =range(1,100)
620  wq
621
622  tabe Xtest2
623  $
624  diffsp Xtest1
625  tabclose
626
627  call delete('Xtest1')
628  call delete('Xtest2')
629endfunc
630
631func Test_diff_move_to()
632  new
633  call setline(1, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
634  diffthis
635  vnew
636  call setline(1, [1, '2x', 3, 4, 4, 5, '6x', 7, '8x', 9, '10x'])
637  diffthis
638  norm ]c
639  call assert_equal(2, line('.'))
640  norm 3]c
641  call assert_equal(9, line('.'))
642  norm 10]c
643  call assert_equal(11, line('.'))
644  norm [c
645  call assert_equal(9, line('.'))
646  norm 2[c
647  call assert_equal(5, line('.'))
648  norm 10[c
649  call assert_equal(2, line('.'))
650  %bwipe!
651endfunc
652
653func Test_diffexpr()
654  CheckExecutable diff
655
656  func DiffExpr()
657    " Prepend some text to check diff type detection
658    call writefile(['warning', '  message'], v:fname_out)
659    silent exe '!diff ' . v:fname_in . ' ' . v:fname_new . '>>' . v:fname_out
660  endfunc
661  set diffexpr=DiffExpr()
662  set diffopt=foldcolumn:0
663
664  enew!
665  call setline(1, ['one', 'two', 'three'])
666  redraw
667  let normattr = screenattr(1, 1)
668  diffthis
669
670  botright vert new
671  call setline(1, ['one', 'two', 'three.'])
672  diffthis
673
674  redraw
675  call assert_equal(normattr, screenattr(1, 1))
676  call assert_equal(normattr, screenattr(2, 1))
677  call assert_notequal(normattr, screenattr(3, 1))
678  diffoff!
679
680  " Try using an non-existing function for 'diffexpr'.
681  set diffexpr=NewDiffFunc()
682  call assert_fails('windo diffthis', ['E117:', 'E97:'])
683  diffoff!
684  %bwipe!
685  set diffexpr& diffopt&
686endfunc
687
688func Test_diffpatch()
689  " The patch program on MS-Windows may fail or hang.
690  CheckExecutable patch
691  CheckUnix
692  new
693  insert
694***************
695*** 1,3 ****
696  1
697! 2
698  3
699--- 1,4 ----
700  1
701! 2x
702  3
703+ 4
704.
705  saveas! Xpatch
706  bwipe!
707  new
708  call assert_fails('diffpatch Xpatch', 'E816:')
709
710  for name in ['Xpatch', 'Xpatch$HOME', 'Xpa''tch']
711    call setline(1, ['1', '2', '3'])
712    if name != 'Xpatch'
713      call rename('Xpatch', name)
714    endif
715    exe 'diffpatch ' . escape(name, '$')
716    call assert_equal(['1', '2x', '3', '4'], getline(1, '$'))
717    if name != 'Xpatch'
718      call rename(name, 'Xpatch')
719    endif
720    bwipe!
721  endfor
722
723  call delete('Xpatch')
724  bwipe!
725endfunc
726
727func Test_diff_too_many_buffers()
728  for i in range(1, 8)
729    exe "new Xtest" . i
730    diffthis
731  endfor
732  new Xtest9
733  call assert_fails('diffthis', 'E96:')
734  %bwipe!
735endfunc
736
737func Test_diff_nomodifiable()
738  new
739  call setline(1, [1, 2, 3, 4])
740  setl nomodifiable
741  diffthis
742  vnew
743  call setline(1, ['1x', 2, 3, 3, 4])
744  diffthis
745  call assert_fails('norm dp', 'E793:')
746  setl nomodifiable
747  call assert_fails('norm do', 'E21:')
748  %bwipe!
749endfunc
750
751func Test_diff_hlID()
752  new
753  call setline(1, [1, 2, 3])
754  diffthis
755  vnew
756  call setline(1, ['1x', 2, 'x', 3])
757  diffthis
758  redraw
759
760  call diff_hlID(-1, 1)->synIDattr("name")->assert_equal("")
761
762  call diff_hlID(1, 1)->synIDattr("name")->assert_equal("DiffChange")
763  call diff_hlID(1, 2)->synIDattr("name")->assert_equal("DiffText")
764  call diff_hlID(2, 1)->synIDattr("name")->assert_equal("")
765  call diff_hlID(3, 1)->synIDattr("name")->assert_equal("DiffAdd")
766  eval 4->diff_hlID(1)->synIDattr("name")->assert_equal("")
767
768  wincmd w
769  call assert_equal(synIDattr(diff_hlID(1, 1), "name"), "DiffChange")
770  call assert_equal(synIDattr(diff_hlID(2, 1), "name"), "")
771  call assert_equal(synIDattr(diff_hlID(3, 1), "name"), "")
772
773  %bwipe!
774endfunc
775
776func Test_diff_filler()
777  new
778  call setline(1, [1, 2, 3, 'x', 4])
779  diffthis
780  vnew
781  call setline(1, [1, 2, 'y', 'y', 3, 4])
782  diffthis
783  redraw
784
785  call assert_equal([0, 0, 0, 0, 0, 0, 0, 1, 0], map(range(-1, 7), 'v:val->diff_filler()'))
786  wincmd w
787  call assert_equal([0, 0, 0, 0, 2, 0, 0, 0], map(range(-1, 6), 'diff_filler(v:val)'))
788
789  %bwipe!
790endfunc
791
792func Test_diff_lastline()
793  enew!
794  only!
795  call setline(1, ['This is a ', 'line with five ', 'rows'])
796  diffthis
797  botright vert new
798  call setline(1, ['This is', 'a line with ', 'four rows'])
799  diffthis
800  1
801  call feedkeys("Je a\<CR>", 'tx')
802  call feedkeys("Je a\<CR>", 'tx')
803  let w1lines = winline()
804  wincmd w
805  $
806  let w2lines = winline()
807  call assert_equal(w2lines, w1lines)
808  bwipe!
809  bwipe!
810endfunc
811
812func WriteDiffFiles(buf, list1, list2)
813  call writefile(a:list1, 'Xfile1')
814  call writefile(a:list2, 'Xfile2')
815  if a:buf
816    call term_sendkeys(a:buf, ":checktime\<CR>")
817  endif
818endfunc
819
820" Verify a screendump with both the internal and external diff.
821func VerifyBoth(buf, dumpfile, extra)
822  " trailing : for leaving the cursor on the command line
823  for cmd in [":set diffopt=filler" . a:extra . "\<CR>:", ":set diffopt+=internal\<CR>:"]
824    call term_sendkeys(a:buf, cmd)
825    if VerifyScreenDump(a:buf, a:dumpfile, {}, cmd =~ 'internal' ? 'internal' : 'external')
826      " don't let the next iteration overwrite the "failed" file.
827      return
828    endif
829  endfor
830
831  " also test unified diff
832  call term_sendkeys(a:buf, ":call SetupUnified()\<CR>:")
833  call term_sendkeys(a:buf, ":redraw!\<CR>:")
834  call VerifyScreenDump(a:buf, a:dumpfile, {}, 'unified')
835  call term_sendkeys(a:buf, ":call StopUnified()\<CR>:")
836endfunc
837
838" Verify a screendump with the internal diff only.
839func VerifyInternal(buf, dumpfile, extra)
840  call term_sendkeys(a:buf, ":diffupdate!\<CR>")
841  " trailing : for leaving the cursor on the command line
842  call term_sendkeys(a:buf, ":set diffopt=internal,filler" . a:extra . "\<CR>:")
843  call TermWait(a:buf)
844  call VerifyScreenDump(a:buf, a:dumpfile, {})
845endfunc
846
847func Test_diff_screen()
848  CheckScreendump
849  CheckFeature menu
850
851  let lines =<< trim END
852      func UnifiedDiffExpr()
853        " Prepend some text to check diff type detection
854        call writefile(['warning', '  message'], v:fname_out)
855        silent exe '!diff -U0 ' .. v:fname_in .. ' ' .. v:fname_new .. '>>' .. v:fname_out
856      endfunc
857      func SetupUnified()
858        set diffexpr=UnifiedDiffExpr()
859        diffupdate
860      endfunc
861      func StopUnified()
862        set diffexpr=
863      endfunc
864  END
865  call writefile(lines, 'XdiffSetup')
866
867  " clean up already existing swap files, just in case
868  call delete('.Xfile1.swp')
869  call delete('.Xfile2.swp')
870
871  " Test 1: Add a line in beginning of file 2
872  call WriteDiffFiles(0, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
873  let buf = RunVimInTerminal('-d -S XdiffSetup Xfile1 Xfile2', {})
874  " Set autoread mode, so that Vim won't complain once we re-write the test
875  " files
876  call term_sendkeys(buf, ":set autoread\<CR>\<c-w>w:set autoread\<CR>\<c-w>w")
877
878  call VerifyBoth(buf, 'Test_diff_01', '')
879
880  " Test 2: Add a line in beginning of file 1
881  call WriteDiffFiles(buf, [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
882  call VerifyBoth(buf, 'Test_diff_02', '')
883
884  " Test 3: Add a line at the end of file 2
885  call WriteDiffFiles(buf, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11])
886  call VerifyBoth(buf, 'Test_diff_03', '')
887
888  " Test 4: Add a line at the end of file 1
889  call WriteDiffFiles(buf, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
890  call VerifyBoth(buf, 'Test_diff_04', '')
891
892  " Test 5: Add a line in the middle of file 2, remove on at the end of file 1
893  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])
894  call VerifyBoth(buf, 'Test_diff_05', '')
895
896  " Test 6: Add a line in the middle of file 1, remove on at the end of file 2
897  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])
898  call VerifyBoth(buf, 'Test_diff_06', '')
899
900  " Variants on test 6 with different context settings
901  call term_sendkeys(buf, ":set diffopt+=context:2\<cr>")
902  call VerifyScreenDump(buf, 'Test_diff_06.2', {})
903  call term_sendkeys(buf, ":set diffopt-=context:2\<cr>")
904  call term_sendkeys(buf, ":set diffopt+=context:1\<cr>")
905  call VerifyScreenDump(buf, 'Test_diff_06.1', {})
906  call term_sendkeys(buf, ":set diffopt-=context:1\<cr>")
907  call term_sendkeys(buf, ":set diffopt+=context:0\<cr>")
908  call VerifyScreenDump(buf, 'Test_diff_06.0', {})
909  call term_sendkeys(buf, ":set diffopt-=context:0\<cr>")
910
911  " Test 7 - 9: Test normal/patience/histogram diff algorithm
912  call WriteDiffFiles(buf, ['#include <stdio.h>', '', '// Frobs foo heartily', 'int frobnitz(int foo)', '{',
913      \ '    int i;', '    for(i = 0; i < 10; i++)', '    {', '        printf("Your answer is: ");',
914      \ '        printf("%d\n", foo);', '    }', '}', '', 'int fact(int n)', '{', '    if(n > 1)', '    {',
915      \ '        return fact(n-1) * n;', '    }', '    return 1;', '}', '', 'int main(int argc, char **argv)',
916      \ '{', '    frobnitz(fact(10));', '}'],
917      \ ['#include <stdio.h>', '', 'int fib(int n)', '{', '    if(n > 2)', '    {',
918      \ '        return fib(n-1) + fib(n-2);', '    }', '    return 1;', '}', '', '// Frobs foo heartily',
919      \ 'int frobnitz(int foo)', '{', '    int i;', '    for(i = 0; i < 10; i++)', '    {',
920      \ '        printf("%d\n", foo);', '    }', '}', '',
921      \ 'int main(int argc, char **argv)', '{', '    frobnitz(fib(10));', '}'])
922  call term_sendkeys(buf, ":diffupdate!\<cr>")
923  call term_sendkeys(buf, ":set diffopt+=internal\<cr>")
924  call VerifyScreenDump(buf, 'Test_diff_07', {})
925
926  call term_sendkeys(buf, ":set diffopt+=algorithm:patience\<cr>")
927  call VerifyScreenDump(buf, 'Test_diff_08', {})
928
929  call term_sendkeys(buf, ":set diffopt+=algorithm:histogram\<cr>")
930  call VerifyScreenDump(buf, 'Test_diff_09', {})
931
932  " Test 10-11: normal/indent-heuristic
933  call term_sendkeys(buf, ":set diffopt&vim\<cr>")
934  call WriteDiffFiles(buf, ['', '  def finalize(values)', '', '    values.each do |v|', '      v.finalize', '    end'],
935      \ ['', '  def finalize(values)', '', '    values.each do |v|', '      v.prepare', '    end', '',
936      \ '    values.each do |v|', '      v.finalize', '    end'])
937  call term_sendkeys(buf, ":diffupdate!\<cr>")
938  call term_sendkeys(buf, ":set diffopt+=internal\<cr>")
939  call VerifyScreenDump(buf, 'Test_diff_10', {})
940
941  " Leave trailing : at commandline!
942  call term_sendkeys(buf, ":set diffopt+=indent-heuristic\<cr>:\<cr>")
943  call VerifyScreenDump(buf, 'Test_diff_11', {}, 'one')
944  " shouldn't matter, if indent-algorithm comes before or after the algorithm
945  call term_sendkeys(buf, ":set diffopt&\<cr>")
946  call term_sendkeys(buf, ":set diffopt+=indent-heuristic,algorithm:patience\<cr>:\<cr>")
947  call VerifyScreenDump(buf, 'Test_diff_11', {}, 'two')
948  call term_sendkeys(buf, ":set diffopt&\<cr>")
949  call term_sendkeys(buf, ":set diffopt+=algorithm:patience,indent-heuristic\<cr>:\<cr>")
950  call VerifyScreenDump(buf, 'Test_diff_11', {}, 'three')
951
952  " Test 12: diff the same file
953  call WriteDiffFiles(buf, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
954  call VerifyBoth(buf, 'Test_diff_12', '')
955
956  " Test 13: diff an empty file
957  call WriteDiffFiles(buf, [], [])
958  call VerifyBoth(buf, 'Test_diff_13', '')
959
960  " Test 14: test diffopt+=icase
961  call WriteDiffFiles(buf, ['a', 'b', 'cd'], ['A', 'b', 'cDe'])
962  call VerifyBoth(buf, 'Test_diff_14', " diffopt+=filler diffopt+=icase")
963
964  " Test 15-16: test diffopt+=iwhite
965  call WriteDiffFiles(buf, ['int main()', '{', '   printf("Hello, World!");', '   return 0;', '}'],
966      \ ['int main()', '{', '   if (0)', '   {', '      printf("Hello, World!");', '      return 0;', '   }', '}'])
967  call term_sendkeys(buf, ":diffupdate!\<cr>")
968  call term_sendkeys(buf, ":set diffopt&vim diffopt+=filler diffopt+=iwhite\<cr>")
969  call VerifyScreenDump(buf, 'Test_diff_15', {})
970  call term_sendkeys(buf, ":set diffopt+=internal\<cr>")
971  call VerifyScreenDump(buf, 'Test_diff_16', {})
972
973  " Test 17: test diffopt+=iblank
974  call WriteDiffFiles(buf, ['a', ' ', 'cd', 'ef', 'xxx'], ['a', 'cd', '', 'ef', 'yyy'])
975  call VerifyInternal(buf, 'Test_diff_17', " diffopt+=iblank")
976
977  " Test 18: test diffopt+=iblank,iwhite / iwhiteall / iwhiteeol
978  call VerifyInternal(buf, 'Test_diff_18', " diffopt+=iblank,iwhite")
979  call VerifyInternal(buf, 'Test_diff_18', " diffopt+=iblank,iwhiteall")
980  call VerifyInternal(buf, 'Test_diff_18', " diffopt+=iblank,iwhiteeol")
981
982  " Test 19: test diffopt+=iwhiteeol
983  call WriteDiffFiles(buf, ['a ', 'x', 'cd', 'ef', 'xx  xx', 'foo', 'bar'], ['a', 'x', 'c d', ' ef', 'xx xx', 'foo', '', 'bar'])
984  call VerifyInternal(buf, 'Test_diff_19', " diffopt+=iwhiteeol")
985
986  " Test 19: test diffopt+=iwhiteall
987  call VerifyInternal(buf, 'Test_diff_20', " diffopt+=iwhiteall")
988
989  " clean up
990  call StopVimInTerminal(buf)
991  call delete('Xfile1')
992  call delete('Xfile2')
993  call delete('XdiffSetup')
994endfunc
995
996func Test_diff_with_cursorline()
997  CheckScreendump
998
999  call writefile([
1000	\ 'hi CursorLine ctermbg=red ctermfg=white',
1001	\ 'set cursorline',
1002	\ 'call setline(1, ["foo","foo","foo","bar"])',
1003	\ 'vnew',
1004	\ 'call setline(1, ["bee","foo","foo","baz"])',
1005	\ 'windo diffthis',
1006	\ '2wincmd w',
1007	\ ], 'Xtest_diff_cursorline')
1008  let buf = RunVimInTerminal('-S Xtest_diff_cursorline', {})
1009
1010  call VerifyScreenDump(buf, 'Test_diff_with_cursorline_01', {})
1011  call term_sendkeys(buf, "j")
1012  call VerifyScreenDump(buf, 'Test_diff_with_cursorline_02', {})
1013  call term_sendkeys(buf, "j")
1014  call VerifyScreenDump(buf, 'Test_diff_with_cursorline_03', {})
1015
1016  " clean up
1017  call StopVimInTerminal(buf)
1018  call delete('Xtest_diff_cursorline')
1019endfunc
1020
1021func Test_diff_with_cursorline_breakindent()
1022  CheckScreendump
1023
1024  call writefile([
1025	\ 'hi CursorLine ctermbg=red ctermfg=white',
1026	\ 'set noequalalways wrap diffopt=followwrap cursorline breakindent',
1027	\ '50vnew',
1028	\ 'call setline(1, ["  ","  ","  ","  "])',
1029	\ 'exe "norm 20Afoo\<Esc>j20Afoo\<Esc>j20Afoo\<Esc>j20Abar\<Esc>"',
1030	\ 'vnew',
1031	\ 'call setline(1, ["  ","  ","  ","  "])',
1032	\ 'exe "norm 20Abee\<Esc>j20Afoo\<Esc>j20Afoo\<Esc>j20Abaz\<Esc>"',
1033	\ 'windo diffthis',
1034	\ '2wincmd w',
1035	\ ], 'Xtest_diff_cursorline_breakindent')
1036  let buf = RunVimInTerminal('-S Xtest_diff_cursorline_breakindent', {})
1037
1038  call term_sendkeys(buf, "gg0")
1039  call VerifyScreenDump(buf, 'Test_diff_with_cul_bri_01', {})
1040  call term_sendkeys(buf, "j")
1041  call VerifyScreenDump(buf, 'Test_diff_with_cul_bri_02', {})
1042  call term_sendkeys(buf, "j")
1043  call VerifyScreenDump(buf, 'Test_diff_with_cul_bri_03', {})
1044  call term_sendkeys(buf, "j")
1045  call VerifyScreenDump(buf, 'Test_diff_with_cul_bri_04', {})
1046
1047  " clean up
1048  call StopVimInTerminal(buf)
1049  call delete('Xtest_diff_cursorline_breakindent')
1050endfunc
1051
1052func Test_diff_with_syntax()
1053  CheckScreendump
1054
1055  let lines =<< trim END
1056  	void doNothing() {
1057	   int x = 0;
1058	   char *s = "hello";
1059	   return 5;
1060	}
1061  END
1062  call writefile(lines, 'Xprogram1.c')
1063  let lines =<< trim END
1064  	void doSomething() {
1065	   int x = 0;
1066	   char *s = "there";
1067	   return 5;
1068	}
1069  END
1070  call writefile(lines, 'Xprogram2.c')
1071
1072  let lines =<< trim END
1073  	edit Xprogram1.c
1074	diffsplit Xprogram2.c
1075  END
1076  call writefile(lines, 'Xtest_diff_syntax')
1077  let buf = RunVimInTerminal('-S Xtest_diff_syntax', {})
1078
1079  call VerifyScreenDump(buf, 'Test_diff_syntax_1', {})
1080
1081  " clean up
1082  call StopVimInTerminal(buf)
1083  call delete('Xtest_diff_syntax')
1084  call delete('Xprogram1.c')
1085  call delete('Xprogram2.c')
1086endfunc
1087
1088func Test_diff_of_diff()
1089  CheckScreendump
1090  CheckFeature rightleft
1091
1092  call writefile([
1093	\ 'call setline(1, ["aa","bb","cc","@@ -3,2 +5,7 @@","dd","ee","ff"])',
1094	\ 'vnew',
1095	\ 'call setline(1, ["aa","bb","cc"])',
1096	\ 'windo diffthis',
1097	\ '1wincmd w',
1098	\ 'setlocal number',
1099	\ ], 'Xtest_diff_diff')
1100  let buf = RunVimInTerminal('-S Xtest_diff_diff', {})
1101
1102  call VerifyScreenDump(buf, 'Test_diff_of_diff_01', {})
1103
1104  call term_sendkeys(buf, ":set rightleft\<cr>")
1105  call VerifyScreenDump(buf, 'Test_diff_of_diff_02', {})
1106
1107  " clean up
1108  call StopVimInTerminal(buf)
1109  call delete('Xtest_diff_diff')
1110endfunc
1111
1112func CloseoffSetup()
1113  enew
1114  call setline(1, ['one', 'two', 'three'])
1115  diffthis
1116  new
1117  call setline(1, ['one', 'tow', 'three'])
1118  diffthis
1119  call assert_equal(1, &diff)
1120  only!
1121endfunc
1122
1123func Test_diff_closeoff()
1124  " "closeoff" included by default: last diff win gets 'diff' reset'
1125  call CloseoffSetup()
1126  call assert_equal(0, &diff)
1127  enew!
1128
1129  " "closeoff" excluded: last diff win keeps 'diff' set'
1130  set diffopt-=closeoff
1131  call CloseoffSetup()
1132  call assert_equal(1, &diff)
1133  diffoff!
1134  enew!
1135endfunc
1136
1137func Test_diff_followwrap()
1138  new
1139  set diffopt+=followwrap
1140  set wrap
1141  diffthis
1142  call assert_equal(1, &wrap)
1143  diffoff
1144  set nowrap
1145  diffthis
1146  call assert_equal(0, &wrap)
1147  diffoff
1148  set diffopt&
1149  bwipe!
1150endfunc
1151
1152func Test_diff_maintains_change_mark()
1153  enew!
1154  call setline(1, ['a', 'b', 'c', 'd'])
1155  diffthis
1156  new
1157  call setline(1, ['a', 'b', 'c', 'e'])
1158  " Set '[ and '] marks
1159  2,3yank
1160  call assert_equal([2, 3], [line("'["), line("']")])
1161  " Verify they aren't affected by the implicit diff
1162  diffthis
1163  call assert_equal([2, 3], [line("'["), line("']")])
1164  " Verify they aren't affected by an explicit diff
1165  diffupdate
1166  call assert_equal([2, 3], [line("'["), line("']")])
1167  bwipe!
1168  bwipe!
1169endfunc
1170
1171" Test for 'patchexpr'
1172func Test_patchexpr()
1173  let g:patch_args = []
1174  func TPatch()
1175    call add(g:patch_args, readfile(v:fname_in))
1176    call add(g:patch_args, readfile(v:fname_diff))
1177    call writefile(['output file'], v:fname_out)
1178  endfunc
1179  set patchexpr=TPatch()
1180
1181  call writefile(['input file'], 'Xinput')
1182  call writefile(['diff file'], 'Xdiff')
1183  %bwipe!
1184  edit Xinput
1185  diffpatch Xdiff
1186  call assert_equal('output file', getline(1))
1187  call assert_equal('Xinput.new', bufname())
1188  call assert_equal(2, winnr('$'))
1189  call assert_true(&diff)
1190
1191  call delete('Xinput')
1192  call delete('Xdiff')
1193  set patchexpr&
1194  delfunc TPatch
1195  %bwipe!
1196endfunc
1197
1198func Test_diff_rnu()
1199  CheckScreendump
1200
1201  let content =<< trim END
1202    call setline(1, ['a', 'a', 'a', 'y', 'b', 'b', 'b', 'b', 'b'])
1203    vnew
1204    call setline(1, ['a', 'a', 'a', 'x', 'x', 'x', 'b', 'b', 'b', 'b', 'b'])
1205    windo diffthis
1206    setlocal number rnu foldcolumn=0
1207  END
1208  call writefile(content, 'Xtest_diff_rnu')
1209  let buf = RunVimInTerminal('-S Xtest_diff_rnu', {})
1210
1211  call VerifyScreenDump(buf, 'Test_diff_rnu_01', {})
1212
1213  call term_sendkeys(buf, "j")
1214  call VerifyScreenDump(buf, 'Test_diff_rnu_02', {})
1215  call term_sendkeys(buf, "j")
1216  call VerifyScreenDump(buf, 'Test_diff_rnu_03', {})
1217
1218  " clean up
1219  call StopVimInTerminal(buf)
1220  call delete('Xtest_diff_rnu')
1221endfunc
1222
1223func Test_diff_multilineconceal()
1224  new
1225  diffthis
1226
1227  new
1228  call matchadd('Conceal', 'a\nb', 9, -1, {'conceal': 'Y'})
1229  set cole=2 cocu=n
1230  call setline(1, ["a", "b"])
1231  diffthis
1232  redraw
1233endfunc
1234
1235func Test_diff_and_scroll()
1236  " this was causing an ml_get error
1237  set ls=2
1238  for i in range(winheight(0) * 2)
1239    call setline(i, i < winheight(0) - 10 ? i : i + 10)
1240  endfor
1241  vnew
1242  for i in range(winheight(0)*2 + 10)
1243    call setline(i, i < winheight(0) - 10 ? 0 : i)
1244  endfor
1245  diffthis
1246  wincmd p
1247  diffthis
1248  execute 'normal ' . winheight(0) . "\<C-d>"
1249
1250  bwipe!
1251  bwipe!
1252  set ls&
1253endfunc
1254
1255func Test_diff_filler_cursorcolumn()
1256  CheckScreendump
1257
1258  let content =<< trim END
1259    call setline(1, ['aa', 'bb', 'cc'])
1260    vnew
1261    call setline(1, ['aa', 'cc'])
1262    windo diffthis
1263    wincmd p
1264    setlocal cursorcolumn foldcolumn=0
1265    norm! gg0
1266    redraw!
1267  END
1268  call writefile(content, 'Xtest_diff_cuc')
1269  let buf = RunVimInTerminal('-S Xtest_diff_cuc', {})
1270
1271  call VerifyScreenDump(buf, 'Test_diff_cuc_01', {})
1272
1273  call term_sendkeys(buf, "l")
1274  call term_sendkeys(buf, "\<C-l>")
1275  call VerifyScreenDump(buf, 'Test_diff_cuc_02', {})
1276  call term_sendkeys(buf, "0j")
1277  call term_sendkeys(buf, "\<C-l>")
1278  call VerifyScreenDump(buf, 'Test_diff_cuc_03', {})
1279  call term_sendkeys(buf, "l")
1280  call term_sendkeys(buf, "\<C-l>")
1281  call VerifyScreenDump(buf, 'Test_diff_cuc_04', {})
1282
1283  " clean up
1284  call StopVimInTerminal(buf)
1285  call delete('Xtest_diff_cuc')
1286endfunc
1287
1288" Test for adding/removing lines inside diff chunks, between diff chunks
1289" and before diff chunks
1290func Test_diff_modify_chunks()
1291  enew!
1292  let w2_id = win_getid()
1293  call setline(1, ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i'])
1294  new
1295  let w1_id = win_getid()
1296  call setline(1, ['a', '2', '3', 'd', 'e', 'f', '7', '8', 'i'])
1297  windo diffthis
1298
1299  " remove a line between two diff chunks and create a new diff chunk
1300  call win_gotoid(w2_id)
1301  5d
1302  call win_gotoid(w1_id)
1303  call diff_hlID(5, 1)->synIDattr('name')->assert_equal('DiffAdd')
1304
1305  " add a line between two diff chunks
1306  call win_gotoid(w2_id)
1307  normal! 4Goe
1308  call win_gotoid(w1_id)
1309  call diff_hlID(4, 1)->synIDattr('name')->assert_equal('')
1310  call diff_hlID(5, 1)->synIDattr('name')->assert_equal('')
1311
1312  " remove all the lines in a diff chunk.
1313  call win_gotoid(w2_id)
1314  7,8d
1315  call win_gotoid(w1_id)
1316  let hl = range(1, 9)->map({_, lnum -> diff_hlID(lnum, 1)->synIDattr('name')})
1317  call assert_equal(['', 'DiffText', 'DiffText', '', '', '', 'DiffAdd',
1318        \ 'DiffAdd', ''], hl)
1319
1320  " remove lines from one diff chunk to just before the next diff chunk
1321  call win_gotoid(w2_id)
1322  call setline(1, ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i'])
1323  2,6d
1324  call win_gotoid(w1_id)
1325  let hl = range(1, 9)->map({_, lnum -> diff_hlID(lnum, 1)->synIDattr('name')})
1326  call assert_equal(['', 'DiffText', 'DiffText', 'DiffAdd', 'DiffAdd',
1327        \ 'DiffAdd', 'DiffAdd', 'DiffAdd', ''], hl)
1328
1329  " remove lines just before the top of a diff chunk
1330  call win_gotoid(w2_id)
1331  call setline(1, ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i'])
1332  5,6d
1333  call win_gotoid(w1_id)
1334  let hl = range(1, 9)->map({_, lnum -> diff_hlID(lnum, 1)->synIDattr('name')})
1335  call assert_equal(['', 'DiffText', 'DiffText', '', 'DiffText', 'DiffText',
1336        \ 'DiffAdd', 'DiffAdd', ''], hl)
1337
1338  " remove line after the end of a diff chunk
1339  call win_gotoid(w2_id)
1340  call setline(1, ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i'])
1341  4d
1342  call win_gotoid(w1_id)
1343  let hl = range(1, 9)->map({_, lnum -> diff_hlID(lnum, 1)->synIDattr('name')})
1344  call assert_equal(['', 'DiffText', 'DiffText', 'DiffAdd', '', '', 'DiffText',
1345        \ 'DiffText', ''], hl)
1346
1347  " remove lines starting from the end of one diff chunk and ending inside
1348  " another diff chunk
1349  call win_gotoid(w2_id)
1350  call setline(1, ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i'])
1351  4,7d
1352  call win_gotoid(w1_id)
1353  let hl = range(1, 9)->map({_, lnum -> diff_hlID(lnum, 1)->synIDattr('name')})
1354  call assert_equal(['', 'DiffText', 'DiffText', 'DiffText', 'DiffAdd',
1355        \ 'DiffAdd', 'DiffAdd', 'DiffAdd', ''], hl)
1356
1357  " removing the only remaining diff chunk should make the files equal
1358  call win_gotoid(w2_id)
1359  call setline(1, ['a', '2', '3', 'x', 'd', 'e', 'f', 'x', '7', '8', 'i'])
1360  8d
1361  let hl = range(1, 10)->map({_, lnum -> diff_hlID(lnum, 1)->synIDattr('name')})
1362  call assert_equal(['', '', '', 'DiffAdd', '', '', '', '', '', ''], hl)
1363  call win_gotoid(w2_id)
1364  4d
1365  call win_gotoid(w1_id)
1366  let hl = range(1, 9)->map({_, lnum -> diff_hlID(lnum, 1)->synIDattr('name')})
1367  call assert_equal(['', '', '', '', '', '', '', '', ''], hl)
1368
1369  %bw!
1370endfunc
1371
1372" vim: shiftwidth=2 sts=2 expandtab
1373