On Thu, Sep 28, 2017 at 11:03:30 +0200, Moritz Barsnick wrote: > On Thu, Sep 28, 2017 at 08:57:12 +0200, Fabian Groffen wrote: > > > I was wondering if anyone has an updated color-status patch, that was > > > written by Thomas Glanzmann? The version I have won't apply to mutt > > > v1.9.1 . > > > > Do you mean this patch? > > > > https://sourceforge.net/p/gentoomuttpatches/code/ci/mutt-1.9/tree/features-extra/0003-feature-status-color.patch > > Probably the one included here, directly from the author himself: > https://marc.info/?l=mutt-dev&m=147176952824395
The attached patch should apply and build fine with 1.9.1. I haven't tested it functionally... (And it lost Thomas's fine comments, as I made it without hg.) Cheers, Moritz
diff -ur mutt-1.9.1/color.c mutt-1.9.1-color-status/color.c --- mutt-1.9.1/color.c 2017-09-23 20:30:45.000000000 +0200 +++ mutt-1.9.1-color-status/color.c 2017-09-28 11:11:52.000000000 +0200 @@ -35,6 +35,7 @@ int ColorDefs[MT_COLOR_MAX]; COLOR_LINE *ColorHdrList = NULL; COLOR_LINE *ColorBodyList = NULL; +COLOR_LINE *ColorStatusList = NULL; COLOR_LINE *ColorIndexList = NULL; /* local to this file */ @@ -517,7 +518,7 @@ static int add_pattern (COLOR_LINE **top, const char *s, int sensitive, int fg, int bg, int attr, BUFFER *err, - int is_index) + int is_index, int match) { /* is_index used to store compiled pattern @@ -588,6 +589,7 @@ } tmp->next = *top; tmp->pattern = safe_strdup (s); + tmp->match = match; #ifdef HAVE_COLOR if(fg != -1 && bg != -1) { @@ -746,7 +748,7 @@ parser_callback_t callback, short dry_run) { int object = 0, attr = 0, fg = 0, bg = 0, q_level = 0; - int r = 0; + int r = 0, match = 0; if(parse_object(buf, s, &object, &q_level, err) == -1) return -1; @@ -754,8 +756,6 @@ if(callback(buf, s, &fg, &bg, &attr, err) == -1) return -1; - /* extract a regular expression if needed */ - if (object == MT_COLOR_HEADER || object == MT_COLOR_BODY || object == MT_COLOR_INDEX) { if (!MoreArgs (s)) @@ -767,7 +767,7 @@ mutt_extract_token (buf, s, 0); } - if (MoreArgs (s)) + if (MoreArgs (s) && object != MT_COLOR_STATUS) { strfcpy (err->data, _("too many arguments"), err->dsize); return (-1); @@ -792,12 +792,37 @@ #endif if (object == MT_COLOR_HEADER) - r = add_pattern (&ColorHdrList, buf->data, 0, fg, bg, attr, err,0); + r = add_pattern (&ColorHdrList, buf->data, 0, fg, bg, attr, err, 0, match); else if (object == MT_COLOR_BODY) - r = add_pattern (&ColorBodyList, buf->data, 1, fg, bg, attr, err, 0); + r = add_pattern (&ColorBodyList, buf->data, 1, fg, bg, attr, err, 0, match); + else if (object == MT_COLOR_STATUS && MoreArgs(s)) + { + /* 'color status fg bg' can have upto 2 arguments: + * 0 arguments: sets the default status color (handled below by else part) + * 1 argument : colorize pattern on match + * 2 arguments: colorize nth submatch of pattern + */ + mutt_extract_token (buf, s, 0); + + if (MoreArgs(s)) { + BUFFER temporary; + memset(&temporary, 0, sizeof(BUFFER)); + mutt_extract_token(&temporary, s, 0); + match = atoi(temporary.data); + FREE(&temporary.data); + } + + if (MoreArgs(s)) + { + strfcpy (err->data, _("too many arguments"), err->dsize); + return (-1); + } + + r = add_pattern (&ColorStatusList, buf->data, 1, fg, bg, attr, err, 0, match); + } else if (object == MT_COLOR_INDEX) { - r = add_pattern (&ColorIndexList, buf->data, 1, fg, bg, attr, err, 1); + r = add_pattern (&ColorIndexList, buf->data, 1, fg, bg, attr, err, 1, match); mutt_set_menu_redraw_full (MENU_MAIN); } else if (object == MT_COLOR_QUOTED) diff -ur mutt-1.9.1/curs_main.c mutt-1.9.1-color-status/curs_main.c --- mutt-1.9.1/curs_main.c 2017-09-23 20:30:45.000000000 +0200 +++ mutt-1.9.1-color-status/curs_main.c 2017-09-28 11:10:07.000000000 +0200 @@ -482,6 +482,117 @@ menu->redraw |= REDRAW_INDEX | REDRAW_STATUS; } +void +mutt_draw_statusline(int cols, char *inbuf) +{ + int i = 0; + int cnt = 0; + int last_color = 0; + int color = 0; + int offset = 0; + int found = 0; + int null_rx = 0; + char buf[2048]; + + struct line_t { + short chunks; + struct syntax_t { + int color; + int first; + int last; + } *syntax; + } lineInfo = { 0, 0 }; + + mutt_format_string(buf, sizeof(buf), cols, cols, 0, ' ', inbuf, + mutt_strlen(inbuf), 0); + + lineInfo.syntax = safe_malloc(sizeof(struct syntax_t)); + lineInfo.syntax[0].first = -1; + lineInfo.syntax[0].last = -1; + lineInfo.syntax[0].color = ColorDefs[MT_COLOR_STATUS]; + lineInfo.chunks = 1; + + do + { + found = 0; + null_rx = 0; + COLOR_LINE *color_line = ColorStatusList; + + if (!buf[offset]) + break; + + while (color_line) + { + regmatch_t pmatch[color_line->match + 1]; + + if (regexec (&color_line->rx, buf + offset, color_line->match + 1, pmatch, + (offset ? REG_NOTBOL : 0)) == 0) + { + if (pmatch[color_line->match].rm_eo != pmatch[color_line->match].rm_so) + { + if (!found) + { + if (++(lineInfo.chunks) > 1) + safe_realloc (&(lineInfo.syntax), + (lineInfo.chunks) * sizeof (struct syntax_t)); + } + i = lineInfo.chunks - 1; + pmatch[color_line->match].rm_so += offset; + pmatch[color_line->match].rm_eo += offset; + if (!found || + pmatch[color_line->match].rm_so < (lineInfo.syntax)[i].first || + (pmatch[color_line->match].rm_so == (lineInfo.syntax)[i].first && + pmatch[color_line->match].rm_eo > (lineInfo.syntax)[i].last)) + { + (lineInfo.syntax)[i].color = color_line->pair; + (lineInfo.syntax)[i].first = pmatch[color_line->match].rm_so; + (lineInfo.syntax)[i].last = pmatch[color_line->match].rm_eo; + } + found = 1; + null_rx = 0; + } + else + null_rx = 1; /* empty regexp; don't add it, but keep looking */ + } + color_line = color_line->next; + } + + if (null_rx) + offset++; /* avoid degenerate cases */ + else + offset = (lineInfo.syntax)[i].last; + } while (found || null_rx); + + for (cnt = 0; cnt < mutt_strlen(buf); cnt++) { + color = lineInfo.syntax[0].color; + for (i = 0; i < lineInfo.chunks; i++) { + /* we assume the chunks are sorted */ + if (cnt > (lineInfo.syntax)[i].last) + continue; + if (cnt < (lineInfo.syntax)[i].first) + break; + if (cnt != (lineInfo.syntax)[i].last) { + color = (lineInfo.syntax)[i].color; + break; + } + /* don't break here, as cnt might be + * in the next chunk as well */ + } + if (color != last_color) { + attrset (color); + last_color = color; + } + addch (buf[cnt]); /* XXX more than one char at a time? */ +#if 0 + waddnstr(stdscr, tgbuf, 10); + SETCOLOR (MT_COLOR_NORMAL); + waddnstr(stdscr, tgbuf + 10, -1); +#endif + } + + safe_free(&lineInfo.syntax); +} + static const struct mapping_t IndexHelp[] = { { N_("Quit"), OP_QUIT }, { N_("Del"), OP_DELETE }, @@ -532,7 +643,7 @@ menu_status_line (buf, sizeof (buf), menu, NONULL (Status)); mutt_window_move (MuttStatusWindow, 0, 0); SETCOLOR (MT_COLOR_STATUS); - mutt_paddstr (MuttStatusWindow->cols, buf); + mutt_draw_statusline (MuttStatusWindow->cols, buf); NORMAL_COLOR; menu->redraw &= ~REDRAW_STATUS; if (option(OPTTSENABLED) && TSSupported) diff -ur mutt-1.9.1/mutt_curses.h mutt-1.9.1-color-status/mutt_curses.h --- mutt-1.9.1/mutt_curses.h 2017-09-23 20:30:45.000000000 +0200 +++ mutt-1.9.1-color-status/mutt_curses.h 2017-09-28 11:07:17.000000000 +0200 @@ -143,6 +143,7 @@ typedef struct color_line { regex_t rx; + int match; /* which substringmap 0 for old behaviour */ char *pattern; pattern_t *color_pattern; /* compiled pattern to speed up index color calculation */ @@ -218,6 +219,7 @@ extern int ColorDefs[]; extern COLOR_LINE *ColorHdrList; extern COLOR_LINE *ColorBodyList; +extern COLOR_LINE *ColorStatusList; extern COLOR_LINE *ColorIndexList; void ci_init_color (void); diff -ur mutt-1.9.1/pager.c mutt-1.9.1-color-status/pager.c --- mutt-1.9.1/pager.c 2017-09-23 20:30:45.000000000 +0200 +++ mutt-1.9.1-color-status/pager.c 2017-09-28 11:09:36.000000000 +0200 @@ -1864,13 +1864,13 @@ size_t l2 = sizeof (buffer); hfi.hdr = (IsHeader (rd->extra)) ? rd->extra->hdr : rd->extra->bdy->hdr; mutt_make_string_info (buffer, l1 < l2 ? l1 : l2, rd->pager_status_window->cols, NONULL (PagerFmt), &hfi, MUTT_FORMAT_MAKEPRINT); - mutt_paddstr (rd->pager_status_window->cols, buffer); + mutt_draw_statusline (rd->pager_status_window->cols, buffer); } else { char bn[STRING]; snprintf (bn, sizeof (bn), "%s (%s)", rd->banner, pager_progress_str); - mutt_paddstr (rd->pager_status_window->cols, bn); + mutt_draw_statusline (rd->pager_status_window->cols, bn); } NORMAL_COLOR; if (option(OPTTSENABLED) && TSSupported) diff -ur mutt-1.9.1/protos.h mutt-1.9.1-color-status/protos.h --- mutt-1.9.1/protos.h 2017-09-23 20:30:45.000000000 +0200 +++ mutt-1.9.1-color-status/protos.h 2017-09-28 11:08:05.000000000 +0200 @@ -181,6 +181,7 @@ void mutt_default_save (char *, size_t, HEADER *); void mutt_display_address (ENVELOPE *); void mutt_display_sanitize (char *); +void mutt_draw_statusline(int n, char *); int mutt_edit_content_type (HEADER *, BODY *, FILE *); void mutt_edit_file (const char *, const char *); void mutt_edit_headers (const char *, const char *, HEADER *, char *, size_t);