From 72521a1697ecc431553fdeb3890e9fca77d00d72 Mon Sep 17 00:00:00 2001 From: Bill-Gray Date: Fri, 6 Jan 2023 20:56:57 -0500 Subject: [PATCH] Scrolling was broken ever since we switched from line-by-line allocation for windows to allocating all lines at once. The existing code rearraged line pointers, so that win->_y[0] was no longer the pointer that ought to be freed. Solution was to scroll without rearranging line pointers. --- pdcurses/scroll.c | 50 +++++++++++++++++++++++------------------------ 1 file changed, 24 insertions(+), 26 deletions(-) diff --git a/pdcurses/scroll.c b/pdcurses/scroll.c index 87b07dcd..2c437914 100644 --- a/pdcurses/scroll.c +++ b/pdcurses/scroll.c @@ -2,6 +2,7 @@ #include #include +#include /*man-start************************************************************** @@ -41,8 +42,8 @@ scroll int wscrl(WINDOW *win, int n) { - int i, l, dir, start, end; - chtype blank, *temp; + int start, end, n_lines; + chtype blank, *tptr, *endptr; /* Check if window scrolls. Valid for window AND pad */ @@ -51,38 +52,35 @@ int wscrl(WINDOW *win, int n) return ERR; blank = win->_bkgd; + start = win->_tmarg; + end = win->_bmarg + 1; + n_lines = end - start; - if (n > 0) + if (n > 0) /* scroll up */ { - start = win->_tmarg; - end = win->_bmarg; - dir = 1; + if( n > n_lines) + n = n_lines; + memmove( win->_y[start], win->_y[start + n], + (n_lines - n) * win->_maxx * sizeof( chtype)); + tptr = win->_y[end - n]; } - else + else /* scroll down */ { - start = win->_bmarg; - end = win->_tmarg; - dir = -1; + n = -n; + if( n > n_lines) + n = n_lines; + memmove( win->_y[start + n], win->_y[start], + (n_lines - n) * win->_maxx * sizeof( chtype)); + tptr = win->_y[win->_tmarg]; } - for (l = 0; l < (n * dir); l++) - { - temp = win->_y[start]; - - /* re-arrange line pointers */ - - for (i = start; i != end; i += dir) - win->_y[i] = win->_y[i + dir]; + /* make blank lines */ - win->_y[end] = temp; - - /* make a blank line */ - - for (i = 0; i < win->_maxx; i++) - *temp++ = blank; - } + endptr = tptr + n * win->_maxx; + while( tptr < endptr) + *tptr++ = blank; - touchline(win, win->_tmarg, win->_bmarg - win->_tmarg + 1); + touchline(win, start, n_lines); PDC_sync(win); return OK;