Mirror of the Vim source from https://github.com/vim/vim
Revision | 69cea3380d9a0ba7f800793c9b91aac991cda000 (tree) |
---|---|
Time | 2022-11-19 21:30:05 |
Author | Bram Moolenaar <Bram@vim....> |
Commiter | Bram Moolenaar |
patch 9.0.0908: with 'smoothscroll' cursor may end up in wrong position
Commit: https://github.com/vim/vim/commit/361895d2a15b4b0bbbb4c009261eab5b3d69ebf1
Author: Yee Cheng Chin <ychin.git@gmail.com>
Date: Sat Nov 19 12:25:16 2022 +0000
@@ -2460,18 +2460,50 @@ | ||
2460 | 2460 | used = curwin->w_cline_height; |
2461 | 2461 | #endif |
2462 | 2462 | |
2463 | - // If the cursor is below botline, we will at least scroll by the height | |
2464 | - // of the cursor line. Correct for empty lines, which are really part of | |
2465 | - // botline. | |
2463 | + // If the cursor is on or below botline, we will at least scroll by the | |
2464 | + // height of the cursor line, which is "used". Correct for empty lines, | |
2465 | + // which are really part of botline. | |
2466 | 2466 | if (cln >= curwin->w_botline) |
2467 | 2467 | { |
2468 | 2468 | scrolled = used; |
2469 | 2469 | if (cln == curwin->w_botline) |
2470 | 2470 | scrolled -= curwin->w_empty_rows; |
2471 | 2471 | min_scrolled = scrolled; |
2472 | - if (cln > curwin->w_botline && curwin->w_p_sms && curwin->w_p_wrap) | |
2473 | - for (linenr_T lnum = curwin->w_botline + 1; lnum <= cln; ++lnum) | |
2474 | - min_scrolled += PLINES_NOFILL(lnum); | |
2472 | + if (curwin->w_p_sms && curwin->w_p_wrap) | |
2473 | + { | |
2474 | + // 'smoothscroll' and 'wrap' are set | |
2475 | + if (cln > curwin->w_botline) | |
2476 | + // add screen lines below w_botline | |
2477 | + for (linenr_T lnum = curwin->w_botline + 1; lnum <= cln; ++lnum) | |
2478 | + min_scrolled += PLINES_NOFILL(lnum); | |
2479 | + | |
2480 | + // Calculate how many screen lines the current top line of window | |
2481 | + // occupies. If it is occupying more than the entire window, we | |
2482 | + // need to scroll the additional clipped lines to scroll past the | |
2483 | + // top line before we can move on to the other lines. | |
2484 | + int top_plines = | |
2485 | +#ifdef FEAT_DIFF | |
2486 | + plines_win_nofill | |
2487 | +#else | |
2488 | + plines_win | |
2489 | +#endif | |
2490 | + (curwin, curwin->w_topline, FALSE); | |
2491 | + int skip_lines = 0; | |
2492 | + int width1 = curwin->w_width - curwin_col_off(); | |
2493 | + int width2 = width1 + curwin_col_off2(); | |
2494 | + // similar formula is used in curs_columns() | |
2495 | + if (curwin->w_skipcol > width1) | |
2496 | + skip_lines += (curwin->w_skipcol - width1) / width2 + 1; | |
2497 | + else if (curwin->w_skipcol > 0) | |
2498 | + skip_lines = 1; | |
2499 | + | |
2500 | + top_plines -= skip_lines; | |
2501 | + if (top_plines > curwin->w_height) | |
2502 | + { | |
2503 | + scrolled += (top_plines - curwin->w_height); | |
2504 | + min_scrolled += (top_plines - curwin->w_height); | |
2505 | + } | |
2506 | + } | |
2475 | 2507 | } |
2476 | 2508 | |
2477 | 2509 | /* |
@@ -3,4 +3,4 @@ | ||
3 | 3 | |h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o |
4 | 4 | |t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o |
5 | 5 | |f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e |
6 | -| @21|3|,|1|0| @9|B|o|t| | |
6 | +| @21|3|,|1|0| @9|6@1|%| |
@@ -0,0 +1,6 @@ | ||
1 | +>f+0&#ffffff0|o|u|r| @35 | |
2 | +|~+0#4040ff13&| @38 | |
3 | +|~| @38 | |
4 | +|~| @38 | |
5 | +|~| @38 | |
6 | +|:+0#0000000&|s|e|t| |s|c|r|o|l@1|o| @9|4|,|1| @10|B|o|t| |
@@ -0,0 +1,6 @@ | ||
1 | +|<+0#4040ff13#ffffff0@2|t+0#0000000&|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t | |
2 | +|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o | |
3 | +|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o | |
4 | +|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |e|n|d| @11 | |
5 | +>f|o|u|r| @35 | |
6 | +@22|4|,|1| @10|B|o|t| |
@@ -0,0 +1,6 @@ | ||
1 | +|<+0#4040ff13#ffffff0@2|t+0#0000000&|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t | |
2 | +|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o | |
3 | +|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o | |
4 | +|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |e|n|d| @11 | |
5 | +|f|o|u>r| @35 | |
6 | +@22|4|,|4| @10|B|o|t| |
@@ -3,4 +3,4 @@ | ||
3 | 3 | |t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o |
4 | 4 | |f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e |
5 | 5 | |x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w |
6 | -| @21|3|,|5|0| @9|B|o|t| | |
6 | +| @21|3|,|5|0| @9|6@1|%| |
@@ -3,4 +3,4 @@ | ||
3 | 3 | | |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |
4 | 4 | |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t |
5 | 5 | | |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t |
6 | -| @21|3|,|2|5|0| @8|B|o|t| | |
6 | +| @21|3|,|2|5|0| @8|6@1|%| |
@@ -3,4 +3,4 @@ | ||
3 | 3 | |t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o |
4 | 4 | |f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e |
5 | 5 | |x|t| |w|i|t|h| |l>o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w |
6 | -| @21|3|,|2|1|0| @8|B|o|t| | |
6 | +| @21|3|,|2|1|0| @8|6@1|%| |
@@ -3,4 +3,4 @@ | ||
3 | 3 | |h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o |
4 | 4 | |t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o |
5 | 5 | |f| |t|e|x|t| |w|i>t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e |
6 | -| @21|3|,|1|7|0| @8|B|o|t| | |
6 | +| @21|3|,|1|7|0| @8|6@1|%| |
@@ -3,4 +3,4 @@ | ||
3 | 3 | |t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o |
4 | 4 | |f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e |
5 | 5 | |x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w |
6 | -| @21|3|,|9|0| @9|B|o|t| | |
6 | +| @21|3|,|9|0| @9|6@1|%| |
@@ -3,4 +3,4 @@ | ||
3 | 3 | |t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o |
4 | 4 | |f| |t|e|x|t| |w|i>t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e |
5 | 5 | |x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w |
6 | -| @21|3|,|1|7|0| @8|B|o|t| | |
6 | +| @21|3|,|1|7|0| @8|6@1|%| |
@@ -3,4 +3,4 @@ | ||
3 | 3 | |t|s| |o|f| |t|e|x>t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o |
4 | 4 | |f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e |
5 | 5 | |x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w |
6 | -|:|s|e|t| |s|c|r|o|l@1|o| @9|3|,|1|3|0| @8|B|o|t| | |
6 | +|:|s|e|t| |s|c|r|o|l@1|o| @9|3|,|1|3|0| @8|6@1|%| |
@@ -3,4 +3,4 @@ | ||
3 | 3 | |f| |t|e|x|t| |w|i>t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e |
4 | 4 | |x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w |
5 | 5 | |i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |l|o|t|s| |o|f| |t|e|x|t| |w|i|t|h| |
6 | -@22|3|,|1|7|0| @8|B|o|t| | |
6 | +@22|3|,|1|7|0| @8|6@1|%| |
@@ -246,7 +246,7 @@ | ||
246 | 246 | |
247 | 247 | let lines =<< trim END |
248 | 248 | vim9script |
249 | - setline(1, ['one', 'two', 'Line' .. (' with lots of text'->repeat(30))]) | |
249 | + setline(1, ['one', 'two', 'Line' .. (' with lots of text'->repeat(30)) .. ' end', 'four']) | |
250 | 250 | set smoothscroll scrolloff=0 |
251 | 251 | normal 3G10|zt |
252 | 252 | END |
@@ -287,6 +287,30 @@ | ||
287 | 287 | call term_sendkeys(buf, "gj") |
288 | 288 | call term_sendkeys(buf, "\<C-Y>") |
289 | 289 | call VerifyScreenDump(buf, 'Test_smooth_long_9', {}) |
290 | + | |
291 | + " 'scrolloff' set to 0, move cursor down one line. | |
292 | + " Cursor should move properly, and since this is a really long line, it will | |
293 | + " be put on top of the screen. | |
294 | + call term_sendkeys(buf, ":set scrolloff=0\<CR>") | |
295 | + call term_sendkeys(buf, "0j") | |
296 | + call VerifyScreenDump(buf, 'Test_smooth_long_10', {}) | |
297 | + | |
298 | + " Repeat the step and move the cursor down again. | |
299 | + " This time, use a shorter long line that is barely long enough to span more | |
300 | + " than one window. Note that the cursor is at the bottom this time because | |
301 | + " Vim prefers to do so if we are scrolling a few lines only. | |
302 | + call term_sendkeys(buf, ":call setline(1, ['one', 'two', 'Line' .. (' with lots of text'->repeat(10)) .. ' end', 'four'])\<CR>") | |
303 | + call term_sendkeys(buf, "3Gzt") | |
304 | + call term_sendkeys(buf, "j") | |
305 | + call VerifyScreenDump(buf, 'Test_smooth_long_11', {}) | |
306 | + | |
307 | + " Repeat the step but this time start it when the line is smooth-scrolled by | |
308 | + " one line. This tests that the offset calculation is still correct and | |
309 | + " still end up scrolling down to the next line with cursor at bottom of | |
310 | + " screen. | |
311 | + call term_sendkeys(buf, "3Gzt") | |
312 | + call term_sendkeys(buf, "\<C-E>j") | |
313 | + call VerifyScreenDump(buf, 'Test_smooth_long_12', {}) | |
290 | 314 | |
291 | 315 | call StopVimInTerminal(buf) |
292 | 316 | endfunc |
@@ -696,6 +696,8 @@ | ||
696 | 696 | static int included_patches[] = |
697 | 697 | { /* Add new patch number below this line */ |
698 | 698 | /**/ |
699 | + 908, | |
700 | +/**/ | |
699 | 701 | 907, |
700 | 702 | /**/ |
701 | 703 | 906, |