From 1166d9ffc8df62ed3eafda4bd6b1312abc475850 Mon Sep 17 00:00:00 2001 From: Rob Swindell <rob@synchro.net> Date: Sat, 3 Dec 2022 15:17:36 -0800 Subject: [PATCH] Add output line pacing support (delay before sending LF) New LINEDELAY and LINEDELAY:n @-codes Another way to pace the terminal output of long display (e.g. ANSI) files. LINEDELAY enables a 1/10th of a second delay before the sending of all LF chars. LINEDELAY:n sets the line_delay duration explicitly to a value in 1/100ths of a second units. So LINEDELAY and LINEDELAY:10 are equivalent. LINEDELAY:0 turns line-pacing off. The original line pacing value is always restored after a printfile/putmsg operation. New JS console.line_delay property (milliseconds) to control via JS. Setting this to a really high value would be bad. Some range enforcement should be added to this and many other console control values (TODO). --- src/sbbs3/con_out.cpp | 5 ++++- src/sbbs3/js_console.cpp | 9 +++++++++ src/sbbs3/prntfile.cpp | 3 +++ src/sbbs3/putmsg.cpp | 36 +++++++++++++++++++++--------------- src/sbbs3/sbbs.h | 1 + 5 files changed, 38 insertions(+), 16 deletions(-) diff --git a/src/sbbs3/con_out.cpp b/src/sbbs3/con_out.cpp index 243b65f6d1..1d03c03d91 100644 --- a/src/sbbs3/con_out.cpp +++ b/src/sbbs3/con_out.cpp @@ -677,8 +677,11 @@ int sbbs_t::outchar(char ch) } else { if(utf8[0] != 0) putcom(utf8); - else + else { + if(ch == '\n' && line_delay) + SLEEP(line_delay); outcom(ch); + } } } if(outchar_esc == ansiState_none) { diff --git a/src/sbbs3/js_console.cpp b/src/sbbs3/js_console.cpp index 118f636d03..4b944deb55 100644 --- a/src/sbbs3/js_console.cpp +++ b/src/sbbs3/js_console.cpp @@ -33,6 +33,7 @@ enum { ,CON_PROP_LNCNTR ,CON_PROP_COLUMN ,CON_PROP_LASTLINELEN + ,CON_PROP_LINE_DELAY ,CON_PROP_ATTR ,CON_PROP_TOS ,CON_PROP_ROW @@ -97,6 +98,9 @@ static JSBool js_console_get(JSContext *cx, JSObject *obj, jsid id, jsval *vp) case CON_PROP_LASTLINELEN: val=sbbs->lastlinelen; break; + case CON_PROP_LINE_DELAY: + val = sbbs->line_delay; + break; case CON_PROP_ATTR: val=sbbs->curatr; break; @@ -244,6 +248,9 @@ static JSBool js_console_set(JSContext *cx, JSObject *obj, jsid id, JSBool stric case CON_PROP_LASTLINELEN: sbbs->lastlinelen=val; break; + case CON_PROP_LINE_DELAY: + sbbs->line_delay = val; + break; case CON_PROP_ATTR: if(JSVAL_IS_STRING(*vp)) { JSVALUE_TO_MSTRING(cx, *vp, sval, NULL); @@ -355,6 +362,7 @@ static jsSyncPropertySpec js_console_properties[] = { { "current_row" ,CON_PROP_ROW ,CON_PROP_FLAGS ,31800}, { "current_column" ,CON_PROP_COLUMN ,CON_PROP_FLAGS ,315}, { "last_line_length" ,CON_PROP_LASTLINELEN ,CON_PROP_FLAGS ,317}, + { "line_delay" ,CON_PROP_LINE_DELAY ,CON_PROP_FLAGS ,320}, { "attributes" ,CON_PROP_ATTR ,CON_PROP_FLAGS ,310}, { "top_of_screen" ,CON_PROP_TOS ,JSPROP_ENUMERATE|JSPROP_READONLY ,310}, { "screen_rows" ,CON_PROP_ROWS ,CON_PROP_FLAGS ,310}, @@ -395,6 +403,7 @@ static const char* con_prop_desc[] = { ,"current 0-based row counter" ,"current 0-based column counter (used to auto-increment <i>line_counter</i> when screen wraps)" ,"length of last line sent to terminal (before a carriage-return or line-wrap)" + ,"duration of delay (in milliseconds) before each line-feed character is sent to the terminal" ,"current display attributes (set with number or string value)" ,"set to <i>true</i> if the terminal cursor is already at the top of the screen - <small>READ ONLY</small>" ,"number of remote terminal screen rows (in lines)" diff --git a/src/sbbs3/prntfile.cpp b/src/sbbs3/prntfile.cpp index 5a1de95822..e1d0147e1a 100644 --- a/src/sbbs3/prntfile.cpp +++ b/src/sbbs3/prntfile.cpp @@ -112,6 +112,7 @@ bool sbbs_t::printfile(const char* fname, long mode, long org_cols, JSObject* ob } else { // Line-at-a-time mode ulong sys_status_sav = sys_status; enum output_rate output_rate = cur_output_rate; + uint org_line_delay = line_delay; uint tmpatr = curatr; ulong orgcon = console; attr_sp = 0; /* clear any saved attributes */ @@ -149,6 +150,8 @@ bool sbbs_t::printfile(const char* fname, long mode, long org_cols, JSObject* ob /* Restore original settings of Forced Pause On/Off */ sys_status &= ~(SS_PAUSEOFF|SS_PAUSEON); sys_status |= (sys_status_sav&(SS_PAUSEOFF|SS_PAUSEON)); + + line_delay = org_line_delay; } if((mode&P_NOABORT || rip) && online==ON_REMOTE) { diff --git a/src/sbbs3/putmsg.cpp b/src/sbbs3/putmsg.cpp index f50be4a478..18216bf9dc 100644 --- a/src/sbbs3/putmsg.cpp +++ b/src/sbbs3/putmsg.cpp @@ -1,7 +1,4 @@ /* Synchronet message/menu display routine */ -// vi: tabstop=4 - -/* $Id: putmsg.cpp,v 1.68 2020/05/11 05:03:47 rswindell Exp $ */ /**************************************************************************** * @format.tab-size 4 (Plain Text/Source Code File Header) * @@ -16,21 +13,9 @@ * See the GNU General Public License for more details: gpl.txt or * * http://www.fsf.org/copyleft/gpl.html * * * - * Anonymous FTP access to the most recent released source is available at * - * ftp://vert.synchro.net, ftp://cvs.synchro.net and ftp://ftp.synchro.net * - * * - * Anonymous CVS access to the development source and modification history * - * is available at cvs.synchro.net:/cvsroot/sbbs, example: * - * cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs login * - * (just hit return, no password is necessary) * - * cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs checkout src * - * * * For Synchronet coding style and modification guidelines, see * * http://www.synchro.net/source.html * * * - * You are encouraged to submit any modifications (preferably in Unix diff * - * format) via e-mail to mods@synchro.net * - * * * Note: If this box doesn't appear square, then you need to fix your tabs. * ****************************************************************************/ @@ -53,6 +38,7 @@ char sbbs_t::putmsg(const char *buf, long mode, long org_cols, JSObject* obj) { uint tmpatr; + uint org_line_delay = line_delay; ulong orgcon=console; ulong sys_status_sav=sys_status; enum output_rate output_rate = cur_output_rate; @@ -80,6 +66,9 @@ char sbbs_t::putmsg(const char *buf, long mode, long org_cols, JSObject* obj) /* Restore original settings of Forced Pause On/Off */ sys_status&=~(SS_PAUSEOFF|SS_PAUSEON); sys_status|=(sys_status_sav&(SS_PAUSEOFF|SS_PAUSEON)); + + line_delay = org_line_delay; + return(ret); } @@ -449,6 +438,23 @@ char sbbs_t::putmsgfrag(const char* buf, long& mode, long org_cols, JSObject* ob mode |= P_NOABORT; continue; } + if(memcmp(str+l, "@LINEDELAY@", 11) == 0) { + l += 11; + line_delay = 100; + continue; + } + if(memcmp(str+l, "@LINEDELAY:", 11) == 0) { + char* p = str + l + 11; + SKIP_DIGIT(p); + if(*p == '@') { + l += 11; + line_delay = atoi(str + l) * 10; + while(str[l] != '@') + l++; + l++; + continue; + } + } bool was_tos = (row == 0); i=show_atcode((char *)str+l, obj); /* returns 0 if not valid @ code */ l+=i; /* i is length of code string */ diff --git a/src/sbbs3/sbbs.h b/src/sbbs3/sbbs.h index 911ab3953e..f20155827c 100644 --- a/src/sbbs3/sbbs.h +++ b/src/sbbs3/sbbs.h @@ -559,6 +559,7 @@ public: char lbuf[LINE_BUFSIZE+1];/* Temp storage for each line output */ int lbuflen; /* Number of characters in line buffer */ uint latr=0; /* Starting attribute of line buffer */ + uint line_delay=0; /* Delay duration (ms) after each line sent */ ulong console; /* Defines current Console settings */ char wordwrap[81]; /* Word wrap buffer */ time_t now=0, /* Used to store current time in Unix format */ -- GitLab