}
/* Print functions */
-static void print_word(printer_t *pr, const char **msg)
+static int word_wrap(printer_t *pr, const char *txt,
+ const char **l, const char **r)
{
- const char *start = *msg;
- while (*start && isspace(*start))
- start++;
- int space = start-*msg;
+ /* In previous word? */
+ if (txt > *l && txt < *r)
+ return 0;
- const char *end = start;
- while (*end && !isspace(*end))
- end++;
- int len = end-start;
+ /* Find left and right ends of the word */
+ *l = txt;
+ while (*txt != '\0' &&
+ *txt != ' ' && *txt != '\t' &&
+ *txt != '\r' && *txt != '\n')
+ txt++;
+ *r = txt;
- if ((pr->col != pr->indent) &&
- (pr->col + space + len > COLS - pr->margin)) {
- pr->col = pr->indent;
- pr->row = pr->row+1;
- space = 0;
+ /* End goes past the margin? */
+ int len = *r - *l;
+ int edge = COLS - pr->margin;
+ if (pr->col + len > edge) {
+ if (pr->indent + len > edge)
+ *r = *l + (edge - pr->indent);
+ return pr->col != pr->indent;
}
- int print = pr->print;
- if (pr->row < pr->top || pr->row >= pr->end)
- print = 0;
-
- if (print)
- mvaddnstr(pr->row, pr->col, *msg, space);
- pr->col += space;
- if (print)
- mvaddnstr(pr->row, pr->col, start, len);
- pr->col += len;
-
- *msg = end;
+ return 0;
}
static void print_string(printer_t *pr, const char *txt)
{
- const char *pick = &txt[pr->pick];
- if (!pr->pick) {
- pr->prow = pr->row;
- pr->pcol = pr->col;
- }
- while (*txt) {
- print_word(pr, &txt);
- if (pr->pick && txt > pick) {
+ int i;
+ const char *l = 0, *r = 0;
+ for (i = 0; txt[i]; i++) {
+ if (word_wrap(pr, &txt[i], &l, &r)) {
+ pr->row += 1;
+ pr->col = pr->indent;
+ }
+ if (i == pr->pick) {
pr->prow = pr->row;
- pr->pcol = pr->col - (txt-pick);
- pr->pick = 0;
+ pr->pcol = pr->col;
+ }
+ switch (txt[i]) {
+ case ' ':
+ pr->col += 1;
+ break;
+ case '\t':
+ pr->col -= pr->indent;
+ pr->col /= 8;
+ pr->col += 1;
+ pr->col *= 8;
+ pr->col += pr->indent;
+ break;
+ case '\r':
+ case '\n':
+ pr->row += 1;
+ pr->col = pr->indent;
+ break;
+ default:
+ if (pr->print &&
+ pr->row >= pr->top &&
+ pr->row < pr->end)
+ mvaddch(pr->row, pr->col, txt[i]);
+ pr->col += 1;
+ break;
}
}
- if (pr->pick) {
+ if (i <= pr->pick) {
pr->prow = pr->row;
pr->pcol = pr->col;
}
- if (pr->pcol < pr->indent)
- pr->pcol = pr->indent;
}
static void print_format(printer_t *pr, const char *fmt, ...)