diff options
author | ache <ache@FreeBSD.org> | 1998-01-02 04:36:51 +0000 |
---|---|---|
committer | ache <ache@FreeBSD.org> | 1998-01-02 04:36:51 +0000 |
commit | 533db3b201ab193b971a34bcef090d11bb0f4d15 (patch) | |
tree | 26b32e41615afb10ff19f8aaa642de47134ce56a /lib/libncurses | |
parent | 8a719f4f6a5228ee1a499af703c7b6cdfa493c59 (diff) | |
download | FreeBSD-src-533db3b201ab193b971a34bcef090d11bb0f4d15.zip FreeBSD-src-533db3b201ab193b971a34bcef090d11bb0f4d15.tar.gz |
1) Redo internal interface to be more latest ncurses-like
2) Fix winsdel called in last line of the window (nothing happens in
old variant)
3) Add range checks to wscrl() and internal soft scroll function
Diffstat (limited to 'lib/libncurses')
-rw-r--r-- | lib/libncurses/curses.priv.h | 1 | ||||
-rw-r--r-- | lib/libncurses/lib_insdel.c | 36 | ||||
-rw-r--r-- | lib/libncurses/lib_scroll.c | 118 |
3 files changed, 82 insertions, 73 deletions
diff --git a/lib/libncurses/curses.priv.h b/lib/libncurses/curses.priv.h index 85f54b7..73e3d7d 100644 --- a/lib/libncurses/curses.priv.h +++ b/lib/libncurses/curses.priv.h @@ -64,6 +64,7 @@ extern WINDOW *makenew(int, int, int, int); extern int timed_wait(int fd, int wait, int *timeleft); extern chtype _nc_background(WINDOW *); extern chtype _nc_render(WINDOW *, chtype); +extern void _nc_scroll_window(WINDOW *, int, short const, short const, chtype); struct try { struct try *child; /* ptr to child. NULL if none */ diff --git a/lib/libncurses/lib_insdel.c b/lib/libncurses/lib_insdel.c index eb30f20..8729efe 100644 --- a/lib/libncurses/lib_insdel.c +++ b/lib/libncurses/lib_insdel.c @@ -12,40 +12,20 @@ ** */ -#include <stdlib.h> #include "curses.priv.h" -#include "terminfo.h" int winsdelln(WINDOW *win, int n) { - int ret, sscroll, stop, sbot; +int code = ERR; T(("winsdel(%x,%d) called", win, n)); - if (n == 0) - return OK; - if (win->_cury == win->_maxy && abs(n) == 1) - return wclrtoeol(win); - if (n < 0 && win->_cury - n > win->_maxy) - /* request to delete too many lines */ - /* should we truncate to an appropriate number? */ - return ERR; - - sscroll = win->_scroll; - stop = win->_regtop; - sbot = win->_regbottom; - - win->_scroll = TRUE; - win->_regtop = win->_cury; - if (win->_regtop > win->_regbottom) - win->_regbottom = win->_maxy; - - ret = wscrl(win, -n); - - win->_scroll = sscroll; - win->_regtop = stop; - win->_regbottom = sbot; - - return ret; + if (win) { + if (n != 0) { + _nc_scroll_window(win, -n, win->_cury, win->_maxy, _nc_background(win)); + } + code = OK; + } + return code; } diff --git a/lib/libncurses/lib_scroll.c b/lib/libncurses/lib_scroll.c index 03e7136..5dd55d6 100644 --- a/lib/libncurses/lib_scroll.c +++ b/lib/libncurses/lib_scroll.c @@ -16,30 +16,30 @@ #include "curses.priv.h" #include "terminfo.h" -void scroll_window(WINDOW *win, int n, int regtop, int regbottom) +void _nc_soft_scroll_window(WINDOW *win, int const n, short const top, short const bottom, chtype blank) { int line, i; chtype *ptr, *temp; chtype **saved; -chtype blank = _nc_background(win); - saved = (chtype **)malloc(sizeof(chtype *) * abs(n)); + saved = (chtype **)calloc(abs(n), sizeof(chtype *)); if (n < 0) { /* save overwritten lines */ - for (i = 0; i < -n; i++) - saved[i] = win->_line[regbottom-i]; + for (i = 0; i < -n && bottom-i >= 0; i++) + saved[i] = win->_line[bottom-i]; /* shift n lines */ - for (line = regbottom; line >= regtop-n; line--) + for (line = bottom; line >= top-n && line >= 0; line--) win->_line[line] = win->_line[line+n]; /* restore saved lines and blank them */ - for (i = 0, line = regtop; line < regtop-n; line++, i++) { - win->_line[line] = saved[i]; + for (i = 0, line = top; line < top-n && line <= win->_maxy; line++, i++) { + if (saved[i]) + win->_line[line] = saved[i]; temp = win->_line[line]; for (ptr = temp; ptr - temp <= win->_maxx; ptr++) *ptr = blank; @@ -47,47 +47,56 @@ chtype blank = _nc_background(win); } else { /* save overwritten lines */ - for (i = 0; i < n; i++) - saved[i] = win->_line[regtop+i]; + for (i = 0; i < n && top+i <= win->_maxy; i++) + saved[i] = win->_line[top+i]; /* shift n lines */ - for (line = regtop; line <= regbottom-n; line++) + for (line = top; line <= bottom-n && line+n <= win->_maxy; line++) win->_line[line] = win->_line[line+n]; /* restore saved lines and blank them */ - for (i = 0, line = regbottom; line > regbottom - n; line--, i++) { - win->_line[line] = saved[i]; + for (i = 0, line = bottom; line > bottom - n && line >= 0; line--, i++) { + if (saved[i]) + win->_line[line] = saved[i]; temp = win->_line[line]; for (ptr = temp; ptr - temp <= win->_maxx; ptr++) *ptr = blank; } } - + /* touchline(win, top, bottom-top+1); */ /* not yet */ free(saved); } -int -wscrl(WINDOW *win, int n) +void _nc_scroll_window(WINDOW *win, int n, short const top, short const bottom, chtype blank) { int physical = FALSE; int i; - T(("wscrl(%x,%d) called", win, n)); + if (top == bottom) { + int sy, sx; - if (! win->_scroll) - return ERR; + getyx(win, sy, sx); + win->_curx = 0; + win->_cury = top; + wclrtoeol(win); + win->_curx = sx; + win->_cury = sy; + return; + } - if (n == 0) - return OK; + if (n > lines) + n = lines; + else if (-n > lines) + n = -lines; /* as an optimization, if the scrolling region is the entire screen scroll the physical screen */ if ( win->_begx == 0 && win->_maxx == columns - 1 && !memory_above && !memory_below - && ((((win->_begy+win->_regtop == 0 && win->_begy+win->_regbottom == lines - 1) + && ((((win->_begy+top == 0 && win->_begy+bottom == lines - 1) || change_scroll_region) && ( (n < 0 && (parm_rindex || scroll_reverse)) || (n > 0 && (parm_index || scroll_forward)) @@ -97,28 +106,28 @@ int i; ) ) ) - physical = TRUE; + physical = TRUE; if (physical == TRUE) { wrefresh(win); - scroll_window(curscr, n, win->_begy+win->_regtop, win->_begy+win->_regbottom); - scroll_window(newscr, n, win->_begy+win->_regtop, win->_begy+win->_regbottom); + _nc_soft_scroll_window(curscr, n, win->_begy+top, win->_begy+bottom, blank); + _nc_soft_scroll_window(newscr, n, win->_begy+top, win->_begy+bottom, blank); } - scroll_window(win, n, win->_regtop, win->_regbottom); + _nc_soft_scroll_window(win, n, top, bottom, blank); if (physical == TRUE) { if (n < 0) { - if ( (( win->_begy+win->_regtop == 0 - && win->_begy+win->_regbottom == lines - 1) + if ( (( win->_begy+top == 0 + && win->_begy+bottom == lines - 1) || change_scroll_region) && (parm_rindex || scroll_reverse) ) { if (change_scroll_region && - (win->_begy+win->_regtop != 0 || win->_begy+win->_regbottom != lines - 1) + (win->_begy+top != 0 || win->_begy+bottom != lines - 1) ) - putp(tparm(change_scroll_region, win->_begy+win->_regtop, win->_begy+win->_regbottom)); + putp(tparm(change_scroll_region, win->_begy+top, win->_begy+bottom)); i = abs(n); - mvcur(-1, -1, win->_begy+win->_regtop, 0); + mvcur(-1, -1, win->_begy+top, 0); if (parm_rindex) { putp(tparm(parm_rindex, i)); } else if (scroll_reverse) { @@ -126,13 +135,13 @@ int i; putp(scroll_reverse); } if (change_scroll_region && - (win->_begy+win->_regtop != 0 || win->_begy+win->_regbottom != lines - 1) + (win->_begy+top != 0 || win->_begy+bottom != lines - 1) ) putp(tparm(change_scroll_region, 0, lines-1)); } else { i = abs(n); - if (win->_begy+win->_regbottom < lines - 1) { - mvcur(-1, -1, win->_begy+win->_regbottom, 0); + if (win->_begy+bottom < lines - 1) { + mvcur(-1, -1, win->_begy+bottom, 0); if (parm_delete_line) { putp(tparm(parm_delete_line, i)); } else if (delete_line) { @@ -141,7 +150,7 @@ int i; i = abs(n); } } - mvcur(-1, -1, win->_begy+win->_regtop, 0); + mvcur(-1, -1, win->_begy+top, 0); if (parm_insert_line) { putp(tparm(parm_insert_line, i)); } else if (insert_line) { @@ -150,16 +159,16 @@ int i; } } } else { - if ( (( win->_begy+win->_regtop == 0 - && win->_begy+win->_regbottom == lines - 1) + if ( (( win->_begy+top == 0 + && win->_begy+bottom == lines - 1) || change_scroll_region) && (parm_index || scroll_forward) ) { if (change_scroll_region && - (win->_begy+win->_regtop != 0 || win->_begy+win->_regbottom != lines - 1) + (win->_begy+top != 0 || win->_begy+bottom != lines - 1) ) - putp(tparm(change_scroll_region, win->_begy+win->_regtop, win->_begy+win->_regbottom)); - mvcur(-1, -1, win->_begy+win->_regbottom, 0); + putp(tparm(change_scroll_region, win->_begy+top, win->_begy+bottom)); + mvcur(-1, -1, win->_begy+bottom, 0); if (parm_index) { putp(tparm(parm_index, n)); } else if (scroll_forward) { @@ -168,11 +177,11 @@ int i; putp(scroll_forward); } if (change_scroll_region && - (win->_begy+win->_regtop != 0 || win->_begy+win->_regbottom != lines - 1) + (win->_begy+top != 0 || win->_begy+bottom != lines - 1) ) putp(tparm(change_scroll_region, 0, lines-1)); } else { - mvcur(-1, -1, win->_begy+win->_regtop, 0); + mvcur(-1, -1, win->_begy+top, 0); if (parm_delete_line) { putp(tparm(parm_delete_line, n)); } else if (delete_line) { @@ -180,8 +189,8 @@ int i; while (i--) putp(delete_line); } - if (win->_begy+win->_regbottom < lines - 1) { - mvcur(win->_begy+win->_regtop, 0, win->_begy+win->_regbottom, 0); + if (win->_begy+bottom < lines - 1) { + mvcur(win->_begy+top, 0, win->_begy+bottom, 0); if (parm_insert_line) { putp(tparm(parm_insert_line, n)); } else if (insert_line) { @@ -195,7 +204,26 @@ int i; mvcur(-1, -1, win->_begy+win->_cury, win->_begx+win->_curx); } else - touchline(win, win->_regtop, win->_regbottom - win->_regtop + 1); + touchline(win, top, bottom - top + 1); +} + + +int +wscrl(WINDOW *win, int n) +{ + T(("wscrl(%x,%d) called", win, n)); + + if (!win || !win->_scroll) + return ERR; + + if (n == 0) + return OK; + + if ((n > (win->_regbottom - win->_regtop)) || + (-n > (win->_regbottom - win->_regtop))) + return ERR; + + _nc_scroll_window(win, n, win->_regtop, win->_regbottom, _nc_background(win)); return OK; } |