mirror of
https://github.com/neovim/neovim.git
synced 2024-12-20 19:25:11 -07:00
vim-patch:8.1.0767: when deleting lines at the bottom signs are misplaced
Problem: When deleting lines at the bottom signs are misplaced.
Solution: Properly update the line number of signs at the end of a buffer
after a delete/undo operation. (Yegappan Lakshmanan, closes vim/vim#3798)
c771bf9016
This commit is contained in:
parent
c5f3dbab35
commit
fb4cf05e44
@ -647,23 +647,31 @@ void sign_mark_adjust(linenr_T line1, linenr_T line2, long amount, long amount_a
|
||||
signlist_T *sign; // a sign in a b_signlist
|
||||
signlist_T *next; // the next sign in a b_signlist
|
||||
signlist_T **lastp; // pointer to pointer to current sign
|
||||
linenr_T new_lnum; // new line number to assign to sign
|
||||
|
||||
curbuf->b_signcols_max = -1;
|
||||
lastp = &curbuf->b_signlist;
|
||||
|
||||
FOR_ALL_SIGNS_IN_BUF(curbuf, sign) {
|
||||
next = sign->next;
|
||||
new_lnum = sign->lnum;
|
||||
if (sign->lnum >= line1 && sign->lnum <= line2) {
|
||||
if (amount == MAXLNUM) {
|
||||
*lastp = next;
|
||||
xfree(sign);
|
||||
continue;
|
||||
} else {
|
||||
sign->lnum += amount;
|
||||
new_lnum += amount;
|
||||
}
|
||||
} else if (sign->lnum > line2) {
|
||||
sign->lnum += amount_after;
|
||||
new_lnum += amount_after;
|
||||
}
|
||||
// If the new sign line number is past the last line in the buffer,
|
||||
// then don't adjust the line number. Otherwise, it will always be past
|
||||
// the last line and will not be visible.
|
||||
if (sign->lnum >= line1 && new_lnum <= curbuf->b_ml.ml_line_count) {
|
||||
sign->lnum = new_lnum;
|
||||
}
|
||||
lastp = &sign->next;
|
||||
}
|
||||
}
|
||||
|
@ -1202,13 +1202,13 @@ func Test_sign_lnum_adjust()
|
||||
enew! | only!
|
||||
|
||||
sign define sign1 text=#> linehl=Comment
|
||||
call setline(1, ['A', 'B', 'C', 'D'])
|
||||
call setline(1, ['A', 'B', 'C', 'D', 'E'])
|
||||
exe 'sign place 5 line=3 name=sign1 buffer=' . bufnr('')
|
||||
let l = sign_getplaced(bufnr(''))
|
||||
call assert_equal(3, l[0].signs[0].lnum)
|
||||
|
||||
" Add some lines before the sign and check the sign line number
|
||||
call append(2, ['AA', 'AB', 'AC'])
|
||||
call append(2, ['BA', 'BB', 'BC'])
|
||||
let l = sign_getplaced(bufnr(''))
|
||||
call assert_equal(6, l[0].signs[0].lnum)
|
||||
|
||||
@ -1217,6 +1217,44 @@ func Test_sign_lnum_adjust()
|
||||
let l = sign_getplaced(bufnr(''))
|
||||
call assert_equal(4, l[0].signs[0].lnum)
|
||||
|
||||
" Insert some lines after the sign and check the sign line number
|
||||
call append(5, ['DA', 'DB'])
|
||||
let l = sign_getplaced(bufnr(''))
|
||||
call assert_equal(4, l[0].signs[0].lnum)
|
||||
|
||||
" Delete some lines after the sign and check the sign line number
|
||||
call deletebufline('', 6, 7)
|
||||
let l = sign_getplaced(bufnr(''))
|
||||
call assert_equal(4, l[0].signs[0].lnum)
|
||||
|
||||
" Break the undo. Otherwise the undo operation below will undo all the
|
||||
" changes made by this function.
|
||||
let &undolevels=&undolevels
|
||||
|
||||
" Delete the line with the sign
|
||||
call deletebufline('', 4)
|
||||
let l = sign_getplaced(bufnr(''))
|
||||
call assert_equal(4, l[0].signs[0].lnum)
|
||||
|
||||
" Undo the delete operation
|
||||
undo
|
||||
let l = sign_getplaced(bufnr(''))
|
||||
call assert_equal(5, l[0].signs[0].lnum)
|
||||
|
||||
" Break the undo
|
||||
let &undolevels=&undolevels
|
||||
|
||||
" Delete few lines at the end of the buffer including the line with the sign
|
||||
" Sign line number should not change (as it is placed outside of the buffer)
|
||||
call deletebufline('', 3, 6)
|
||||
let l = sign_getplaced(bufnr(''))
|
||||
call assert_equal(5, l[0].signs[0].lnum)
|
||||
|
||||
" Undo the delete operation. Sign should be restored to the previous line
|
||||
undo
|
||||
let l = sign_getplaced(bufnr(''))
|
||||
call assert_equal(5, l[0].signs[0].lnum)
|
||||
|
||||
sign unplace * group=*
|
||||
sign undefine sign1
|
||||
enew!
|
||||
|
Loading…
Reference in New Issue
Block a user