aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKaz Kylheku <kaz@kylheku.com>2022-04-27 00:21:47 -0700
committerKaz Kylheku <kaz@kylheku.com>2022-04-27 00:21:47 -0700
commit66c11a4add855941754df81e9ebd43ddca8e134c (patch)
treee2a67ef4a7ce74be2ece73cc1218a680b213865f
parent14c644016b22c33b3b4de130338e411ebb4e7e1f (diff)
downloadpw-66c11a4add855941754df81e9ebd43ddca8e134c.tar.gz
pw-66c11a4add855941754df81e9ebd43ddca8e134c.tar.bz2
pw-66c11a4add855941754df81e9ebd43ddca8e134c.zip
Snapshot what is displayed.
-rw-r--r--pw.c50
1 files changed, 37 insertions, 13 deletions
diff --git a/pw.c b/pw.c
index e9026b3..e7669f1 100644
--- a/pw.c
+++ b/pw.c
@@ -26,6 +26,9 @@ typedef struct dstr {
#define dstr_of(str) ((dstr *) ((str) - sizeof (dstr)))
+char **snapshot;
+int snaplines;
+
static void panic(const char *fmt, ...)
{
va_list vl;
@@ -189,13 +192,20 @@ static void drawstatus(unsigned stat, char *cmd)
static void redraw(char **circbuf, int nlines, int hpos,
int columns, unsigned stat, char *cmd)
{
+ if (snapshot) {
+ for (int i = 0; i < snaplines; i++)
+ dsdrop(snapshot[i]);
+ }
+ snaplines = nlines;
printf("\r\033[%dA\033[J", nlines);
- for (int i = 0; i < nlines; i++)
+ for (int i = 0; i < nlines; i++) {
drawline(circbuf[i], hpos, columns);
+ snapshot[i] = dsref(circbuf[i]);
+ }
drawstatus(stat, cmd);
}
-static void execute(char *cmd, char **circbuf, int nlines)
+static void execute(char *cmd)
{
char *arg = cmd + 1 + strspn(cmd + 1, " \t");
@@ -212,8 +222,8 @@ static void execute(char *cmd, char **circbuf, int nlines)
break;
}
- for (int i = 0; ok && i < nlines; i++)
- if (fprintf(f, "%s\n", circbuf[i]) < 0) {
+ for (int i = 0; ok && i < snaplines; i++)
+ if (fprintf(f, "%s\n", snapshot[i]) < 0) {
sprintf(cmd, "write error!");
ok = 0;
break;
@@ -235,8 +245,8 @@ static void execute(char *cmd, char **circbuf, int nlines)
break;
}
- for (int i = 0; i < nlines && ok; i++)
- if (fprintf(p, "%s\n", circbuf[i]) < 0) {
+ for (int i = 0; i < snaplines && ok; i++)
+ if (fprintf(p, "%s\n", snapshot[i]) < 0) {
sprintf(cmd, "write error!");
ok = 0;
break;
@@ -307,7 +317,9 @@ int main(int argc, char **argv)
if (maxlines <= 0 || maxlines > 1000)
error("%d is an unreasonable number of lines to display", maxlines);
- if ((circbuf = malloc(sizeof *circbuf * maxlines)) == 0)
+ if ((circbuf = calloc(sizeof *circbuf, maxlines)) == 0)
+ panic("out of memory");
+ if ((snapshot = calloc(sizeof *snapshot, maxlines)) == 0)
panic("out of memory");
if (isatty(fd)) {
@@ -388,10 +400,15 @@ int main(int argc, char **argv)
stat |= stat_dirty;
}
} else {
- circbuf[nlines++] = line;
- clear_cur_line();
- drawline(line, hpos, columns);
- drawstatus(stat, colcmd);
+ if ((stat & stat_susp)) {
+ dsdrop(line);
+ } else {
+ circbuf[nlines++] = line;
+ snapshot[snaplines++] = dsref(line);
+ clear_cur_line();
+ drawline(line, hpos, columns);
+ drawstatus(stat, colcmd);
+ }
}
} else {
if (auto_quit)
@@ -438,8 +455,15 @@ int main(int argc, char **argv)
stat |= stat_dirty;
break;
case ' ':
- if ((stat & stat_eof) == 0)
+ if ((stat & stat_eof) == 0) {
stat |= (stat_dirty | stat_susp);
+ for (int i = 0; i < nlines || i < snaplines; i++) {
+ if (i < nlines)
+ dsdrop(circbuf[i]);
+ circbuf[i] = (i < snaplines) ? dsref(snapshot[i]) : 0;
+ }
+ nlines = snaplines;
+ }
break;
case 13:
stat &= ~stat_susp;
@@ -480,7 +504,7 @@ int main(int argc, char **argv)
kbd_state = kbd_cmd;
stat |= stat_dirty;
if (ch == 13 && cmdbuf[0]) {
- execute(cmdbuf, circbuf, nlines);
+ execute(cmdbuf);
stat &= ~stat_dirty;
kbd_state = kbd_result;
break;