0
0
mirror of https://github.com/vim/vim.git synced 2025-09-29 04:34:16 -04:00

patch 9.0.0913: only change in current window triggers the WinScrolled event

Problem:    Only a change in the current window triggers the WinScrolled
            event.
Solution:   Trigger WinScrolled if any window scrolled or changed size.
            (issue #11576)
This commit is contained in:
Bram Moolenaar
2022-11-19 21:18:11 +00:00
parent c896adbcde
commit 0a60f79fd0
7 changed files with 128 additions and 36 deletions

View File

@@ -2843,44 +2843,76 @@ trigger_winclosed(win_T *win)
}
/*
* Trigger WinScrolled for "curwin" if needed.
* Make a snapshot of all the window scroll positions and sizes of the current
* tab page.
*/
static void
snapshot_windows_scroll_size(void)
{
win_T *wp;
FOR_ALL_WINDOWS(wp)
{
wp->w_last_topline = wp->w_topline;
wp->w_last_leftcol = wp->w_leftcol;
wp->w_last_skipcol = wp->w_skipcol;
wp->w_last_width = wp->w_width;
wp->w_last_height = wp->w_height;
}
}
static int did_initial_scroll_size_snapshot = FALSE;
void
may_make_initial_scroll_size_snapshot(void)
{
if (!did_initial_scroll_size_snapshot)
{
did_initial_scroll_size_snapshot = TRUE;
snapshot_windows_scroll_size();
}
}
/*
* Trigger WinScrolled if any window scrolled or changed size.
*/
void
may_trigger_winscrolled(void)
{
static int recursive = FALSE;
if (recursive || !has_winscrolled())
if (recursive
|| !has_winscrolled()
|| !did_initial_scroll_size_snapshot)
return;
win_T *wp = curwin;
if (wp->w_last_topline != wp->w_topline
|| wp->w_last_leftcol != wp->w_leftcol
|| wp->w_last_skipcol != wp->w_skipcol
|| wp->w_last_width != wp->w_width
|| wp->w_last_height != wp->w_height)
{
// "curwin" may be different from the actual current window, make sure
// it can be restored.
window_layout_lock();
recursive = TRUE;
char_u winid[NUMBUFLEN];
vim_snprintf((char *)winid, sizeof(winid), "%d", wp->w_id);
apply_autocmds(EVENT_WINSCROLLED, winid, winid, FALSE, wp->w_buffer);
recursive = FALSE;
window_layout_unlock();
// an autocmd may close the window, "wp" may be invalid now
if (win_valid_any_tab(wp))
win_T *wp;
FOR_ALL_WINDOWS(wp)
if (wp->w_last_topline != wp->w_topline
|| wp->w_last_leftcol != wp->w_leftcol
|| wp->w_last_skipcol != wp->w_skipcol
|| wp->w_last_width != wp->w_width
|| wp->w_last_height != wp->w_height)
{
wp->w_last_topline = wp->w_topline;
wp->w_last_leftcol = wp->w_leftcol;
wp->w_last_skipcol = wp->w_skipcol;
wp->w_last_width = wp->w_width;
wp->w_last_height = wp->w_height;
// WinScrolled is triggered only once, even when multiple windows
// scrolled or changed size. Store the current values before
// triggering the event, if a scroll or resize happens as a side
// effect then WinScrolled is triggered again later.
snapshot_windows_scroll_size();
// "curwin" may be different from the actual current window, make
// sure it can be restored.
window_layout_lock();
recursive = TRUE;
char_u winid[NUMBUFLEN];
vim_snprintf((char *)winid, sizeof(winid), "%d", wp->w_id);
apply_autocmds(EVENT_WINSCROLLED, winid, winid, FALSE,
wp->w_buffer);
recursive = FALSE;
window_layout_unlock();
break;
}
}
}
/*