typetest

Typing speed benchmarker
git clone https://git.sinitax.com/sinitax/typetest
Log | Files | Refs | LICENSE | sfeed.txt

commit bae29417270798f60d0348c22cd9fb21b5f3d8f8
parent 6cb461a040f4b53f0f01421da92007fc682a7310
Author: Louis Burda <quent.burda@gmail.com>
Date:   Tue, 22 Jun 2021 00:05:34 +0200

Added preview of next line and fixed input parsing

Diffstat:
Mmain.c | 61++++++++++++++++++++++++++++++++++++++++++-------------------
1 file changed, 42 insertions(+), 19 deletions(-)

diff --git a/main.c b/main.c @@ -36,11 +36,13 @@ enum { STYLE_MAGENTA_FG = 35, STYLE_CYAN_FG = 36, STYLE_WHITE_FG = 37, + STYLE_GREY_FG = 90, }; static const int style_wrong[] = { STYLE_RED_FG, STYLE_BOLD, STYLE_END }; static const int style_right[] = { STYLE_GREEN_FG, STYLE_END }; static const int style_reset[] = { STYLE_RESET, STYLE_END }; +static const int style_preview[] = { STYLE_GREY_FG, STYLE_END }; struct termios oldt; @@ -53,7 +55,7 @@ die(const char *fmtstr, ...) va_list ap; va_start(ap, fmtstr); - vprintf(fmtstr, ap); + vfprintf(stderr, fmtstr, ap); va_end(ap); exit(EXIT_FAILURE); @@ -84,22 +86,20 @@ time_sub(struct timespec *new, struct timespec *old) } int -type(const char *text) +type(const char *text, const char *preview) { char input[1024]; int c, right, wrong, tlen; struct timespec start = { 0 }, end; float cps; - printf("%s", text); - tlen = strlen(text); - right = wrong = 0; - while ((c = getchar()) > 0) { - printf("\x1b[2K"); /* clear line */ - printf("\r"); /* cursor to beginning of line */ + c = right = wrong = 0; + do { + printf("\r\x1b[2K"); /* goto beginning of row and clear */ + printf("\x1b[1A\x1b[2K"); /* up a row and clear */ - if (!start.tv_sec) + if (c && !start.tv_sec) clock_gettime(CLOCK_REALTIME, &start); switch (c) { @@ -108,9 +108,10 @@ type(const char *text) return 1; case C_DEL: if (wrong) wrong--; - else right--; + else if (right) right--; break; case u'\n': + case u'\0': break; default: if (right + wrong == tlen) break; @@ -127,8 +128,12 @@ type(const char *text) print_style(style_reset); printf("%.*s", tlen - right - wrong, text + right + wrong); + print_style(style_preview); + printf("\n\r%s", preview); + print_style(style_reset); + if (!wrong && right + wrong == tlen) break; - } + } while ((c = getchar()) > 0); clock_gettime(CLOCK_REALTIME, &end); time_sub(&end, &start); @@ -137,7 +142,22 @@ type(const char *text) if (!typed) gcps = cps; else gcps = LINTERP(gcps, cps, typed * 1.f / (typed + tlen)); - printf("\n\r"); + return 0; +} + +int +getl(FILE *f, char *buf, size_t size) +{ + int i; + + do { + if (!fgets(buf, size, f)) + return 1; + + for (i = strlen(buf) - 1; *buf; buf[i--] = '\0') + if (!strchr("\n\r", buf[i])) break; + } while (!*buf); + return 0; } @@ -151,7 +171,8 @@ int main(int argc, const char **argv) { struct termios t; - char linebuf[256]; + char cur[256], next[256]; + int eof; FILE *f; if (argc < 2) @@ -170,12 +191,14 @@ main(int argc, const char **argv) if (!tcsetattr(0, TCSANOW, &t)) atexit(reset); - while (fgets(linebuf, sizeof(linebuf), f) > 0) { - if (!*linebuf) break; - if (linebuf[strlen(linebuf)-1] == '\n') - linebuf[strlen(linebuf)-1] = '\0'; - if (!*linebuf) continue; - if (type(linebuf)) break; + if (getl(f, next, sizeof(next))) + die("Empty input file\n"); + + printf("\n"); + for (eof = 0; !eof; ) { + memcpy(cur, next, sizeof(cur)); + eof |= getl(f, next, sizeof(next)); + if (type(cur, eof ? "" : next)) break; } printf("CPM: %0.2f\n\r", gcps * 60);