mirror of
https://github.com/vim/vim.git
synced 2026-05-28 00:21:37 +02:00
patch 9.2.0208: MS-Windows: excessive scroll-behaviour with go+=!
Problem: MS-Windows: excessive scroll-behaviour with go+=! after
switching to ConPTY as default (after v9.2.0048).
Solution: Use tl_cursor_pos to determine the number of lines to scroll
(Yasuhiro Matsumoto).
Since patch 9.2.0048 (71cc1b12) made ConPTY the default on Windows 11,
running :!cmd with guioptions+=! scrolls up the entire window height
instead of only the output lines.
ConPTY damages all terminal rows on initialization even when they are
empty, which causes tl_dirty_row_end to equal Rows. The scroll-up loop
in update_system_term() then scrolls the full screen because
(Rows - tl_toprow) < tl_dirty_row_end is always true until tl_toprow
reaches 0.
Use the cursor position instead of tl_dirty_row_end for the scroll
calculation, since it reflects where actual content has been written.
The scroll bug only occurs with ConPTY. With winpty the terminal
finishes too quickly for the timer-based screen check to work.
closes: #19735
Signed-off-by: Yasuhiro Matsumoto <mattn.jp@gmail.com>
Signed-off-by: Christian Brabandt <cb@256bit.org>
This commit is contained in:
committed by
Christian Brabandt
parent
6391a38e5e
commit
67ae763557
+4
-1
@@ -4008,8 +4008,11 @@ update_system_term(term_T *term)
|
||||
screen = vterm_obtain_screen(term->tl_vterm);
|
||||
|
||||
// Scroll up to make more room for terminal lines if needed.
|
||||
// Use the cursor position to determine how much to scroll, because
|
||||
// ConPTY may damage all rows on initialization even when most are
|
||||
// empty, which would cause unnecessary scrolling.
|
||||
while (term->tl_toprow > 0
|
||||
&& (Rows - term->tl_toprow) < term->tl_dirty_row_end)
|
||||
&& (Rows - term->tl_toprow) < term->tl_cursor_pos.row + 1)
|
||||
{
|
||||
int save_p_more = p_more;
|
||||
|
||||
|
||||
@@ -960,6 +960,47 @@ func Test_gui_run_cmd_in_terminal()
|
||||
let &guioptions = save_guioptions
|
||||
endfunc
|
||||
|
||||
" Test that :! with guioptions+=! doesn't scroll more than necessary.
|
||||
" With ConPTY on Windows 11, the terminal may damage all rows on init,
|
||||
" which previously caused the entire screen to scroll up.
|
||||
func Test_gui_system_term_scroll()
|
||||
CheckFeature terminal
|
||||
CheckFeature conpty
|
||||
let save_guioptions = &guioptions
|
||||
set guioptions+=!
|
||||
|
||||
enew
|
||||
call setline(1, repeat(['AAAA'], &lines + 5))
|
||||
redraw
|
||||
|
||||
" Timer fires during terminal_loop to check the screen while the command
|
||||
" is still running. Row 1 should still show buffer content if scrolling
|
||||
" is correct.
|
||||
let g:system_term_row1 = ''
|
||||
func s:CheckScroll(timer)
|
||||
let g:system_term_row1 = screenstring(1, 1)
|
||||
endfunc
|
||||
call timer_start(200, function('s:CheckScroll'))
|
||||
|
||||
" Use a command that runs long enough for the timer to fire during
|
||||
" terminal_loop. wait_return() returns immediately when sourcing a script,
|
||||
" so the timer must fire before the command finishes.
|
||||
if has('win32')
|
||||
!ping -n 2 127.0.0.1 > nul
|
||||
else
|
||||
!sleep 1
|
||||
endif
|
||||
|
||||
" With the ConPTY scroll bug, the screen scrolled up entirely and row 1
|
||||
" became blank. With the fix, only the output lines scroll and the buffer
|
||||
" content remains visible near the top of the screen.
|
||||
call assert_equal('A', g:system_term_row1)
|
||||
|
||||
%bwipe!
|
||||
delfunc s:CheckScroll
|
||||
let &guioptions = save_guioptions
|
||||
endfunc
|
||||
|
||||
func Test_gui_recursive_mapping()
|
||||
nmap ' <C-W>
|
||||
nmap <C-W>a :let didit = 1<CR>
|
||||
|
||||
@@ -734,6 +734,8 @@ static char *(features[]) =
|
||||
|
||||
static int included_patches[] =
|
||||
{ /* Add new patch number below this line */
|
||||
/**/
|
||||
208,
|
||||
/**/
|
||||
207,
|
||||
/**/
|
||||
|
||||
Reference in New Issue
Block a user