alpine/chappa-colortext.patch
2013-09-04 11:16:41 +00:00

523 lines
18 KiB
Diff

---
alpine/confscroll.c | 3
pith/conf.c | 14 +++
pith/conf.h | 4 +
pith/conftype.h | 3
pith/mailview.c | 192 ++++++++++++++++++++++++++++++++++++++++++++++++++++
pith/mailview.h | 15 ++++
pith/pine.hlp | 63 +++++++++++++++++
pith/state.c | 3
pith/state.h | 2
pith/text.c | 9 ++
10 files changed, 308 insertions(+)
Index: alpine-2.11/alpine/confscroll.c
===================================================================
--- alpine-2.11.orig/alpine/confscroll.c
+++ alpine-2.11/alpine/confscroll.c
@@ -5183,6 +5183,9 @@ fix_side_effects(struct pine *ps, struct
clear_index_cache(ps->mail_stream, 0);
}
+ else if(var == &ps->vars[V_SPECIAL_TEXT]){
+ regex_pattern(ps->VAR_SPECIAL_TEXT);
+ }
else if(var == &ps->vars[V_INIT_CMD_LIST]){
if(!revert)
q_status_message(SM_ASYNC, 0, 3,
Index: alpine-2.11/pith/conf.c
===================================================================
--- alpine-2.11.orig/pith/conf.c
+++ alpine-2.11/pith/conf.c
@@ -228,6 +228,8 @@ CONF_TXT_T cf_text_deadlets[] = "Specif
CONF_TXT_T cf_text_fillcol[] = "Specifies the column of the screen where the composer should wrap.";
+CONF_TXT_T cf_special_text_color[] = "Specifies a comma separated list of text and regular expresions that Pine\n# will highlight";
+
CONF_TXT_T cf_text_replystr[] = "Specifies the string to insert when replying to a message.";
CONF_TXT_T cf_text_quotereplstr[] = "Specifies the string to replace quotes with when viewing a message.";
@@ -560,6 +562,8 @@ static struct variable variables[] = {
NULL, cf_text_speller},
{"composer-wrap-column", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0,
NULL, cf_text_fillcol},
+{"special-text-color", 0, 1, 0, 1, 1, 1, 0, 0, 0, 1, 0,
+ NULL, cf_special_text_color},
{"reply-indent-string", 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0,
NULL, cf_text_replystr},
{"reply-leadin", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0,
@@ -817,6 +821,8 @@ static struct variable variables[] = {
{"incoming-unseen-background-color", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0},
{"signature-foreground-color", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0},
{"signature-background-color", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0},
+{"special-text-foreground-color", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0},
+{"special-text-background-color", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0},
{"prompt-foreground-color", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0},
{"prompt-background-color", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0},
{"header-general-foreground-color", 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0},
@@ -1985,6 +1991,8 @@ init_vars(struct pine *ps, void (*cmds_f
set_current_val(&vars[V_FORM_FOLDER], TRUE, TRUE);
set_current_val(&vars[V_EDITOR], TRUE, TRUE);
set_current_val(&vars[V_SPELLER], TRUE, TRUE);
+ set_current_val(&vars[V_SPECIAL_TEXT], TRUE, TRUE);
+ regex_pattern(VAR_SPECIAL_TEXT);
set_current_val(&vars[V_IMAGE_VIEWER], TRUE, TRUE);
set_current_val(&vars[V_BROWSER], TRUE, TRUE);
set_current_val(&vars[V_SMTP_SERVER], TRUE, TRUE);
@@ -6483,6 +6491,7 @@ set_current_color_vals(struct pine *ps)
set_color_val(&vars[V_IND_OP_FORE_COLOR], 0);
set_color_val(&vars[V_INCUNSEEN_FORE_COLOR], 0);
set_color_val(&vars[V_SIGNATURE_FORE_COLOR], 0);
+ set_color_val(&vars[V_SPECIAL_TEXT_FORE_COLOR], 0);
set_current_val(&ps->vars[V_INDEX_TOKEN_COLORS], TRUE, TRUE);
set_current_val(&ps->vars[V_VIEW_HDR_COLORS], TRUE, TRUE);
@@ -7664,6 +7673,8 @@ config_help(int var, int feature)
return(h_config_scroll_margin);
case V_DEADLETS :
return(h_config_deadlets);
+ case V_SPECIAL_TEXT :
+ return(h_config_special_text_to_color);
case V_FILLCOL :
return(h_config_composer_wrap_column);
case V_TCPOPENTIMEO :
@@ -7829,6 +7840,9 @@ config_help(int var, int feature)
case V_SIGNATURE_FORE_COLOR :
case V_SIGNATURE_BACK_COLOR :
return(h_config_signature_color);
+ case V_SPECIAL_TEXT_FORE_COLOR :
+ case V_SPECIAL_TEXT_BACK_COLOR :
+ return(h_config_special_text_color);
case V_PROMPT_FORE_COLOR :
case V_PROMPT_BACK_COLOR :
return(h_config_prompt_color);
Index: alpine-2.11/pith/conf.h
===================================================================
--- alpine-2.11.orig/pith/conf.h
+++ alpine-2.11/pith/conf.h
@@ -161,6 +161,8 @@
#define GLO_EDITOR vars[V_EDITOR].global_val.l
#define VAR_SPELLER vars[V_SPELLER].current_val.p
#define GLO_SPELLER vars[V_SPELLER].global_val.p
+#define VAR_SPECIAL_TEXT vars[V_SPECIAL_TEXT].current_val.l
+#define GLO_SPECIAL_TEXT vars[V_SPECIAL_TEXT].global_val.l
#define VAR_FILLCOL vars[V_FILLCOL].current_val.p
#define GLO_FILLCOL vars[V_FILLCOL].global_val.p
#define VAR_DEADLETS vars[V_DEADLETS].current_val.p
@@ -456,6 +458,8 @@
#define GLO_SIGNATURE_FORE_COLOR vars[V_SIGNATURE_FORE_COLOR].global_val.p
#define VAR_SIGNATURE_BACK_COLOR vars[V_SIGNATURE_BACK_COLOR].current_val.p
#define GLO_SIGNATURE_BACK_COLOR vars[V_SIGNATURE_BACK_COLOR].global_val.p
+#define VAR_SPECIAL_TEXT_FORE_COLOR vars[V_SPECIAL_TEXT_FORE_COLOR].current_val.p
+#define VAR_SPECIAL_TEXT_BACK_COLOR vars[V_SPECIAL_TEXT_BACK_COLOR].current_val.p
#define VAR_PROMPT_FORE_COLOR vars[V_PROMPT_FORE_COLOR].current_val.p
#define VAR_PROMPT_BACK_COLOR vars[V_PROMPT_BACK_COLOR].current_val.p
#define VAR_VIEW_HDR_COLORS vars[V_VIEW_HDR_COLORS].current_val.l
Index: alpine-2.11/pith/conftype.h
===================================================================
--- alpine-2.11.orig/pith/conftype.h
+++ alpine-2.11/pith/conftype.h
@@ -80,6 +80,7 @@ typedef enum { V_PERSONAL_NAME = 0
, V_EDITOR
, V_SPELLER
, V_FILLCOL
+ , V_SPECIAL_TEXT
, V_REPLY_STRING
, V_REPLY_INTRO
, V_QUOTE_REPLACE_STRING
@@ -230,6 +231,8 @@ typedef enum { V_PERSONAL_NAME = 0
, V_INCUNSEEN_BACK_COLOR
, V_SIGNATURE_FORE_COLOR
, V_SIGNATURE_BACK_COLOR
+ , V_SPECIAL_TEXT_FORE_COLOR
+ , V_SPECIAL_TEXT_BACK_COLOR
, V_PROMPT_FORE_COLOR
, V_PROMPT_BACK_COLOR
, V_HEADER_GENERAL_FORE_COLOR
Index: alpine-2.11/pith/mailview.c
===================================================================
--- alpine-2.11.orig/pith/mailview.c
+++ alpine-2.11/pith/mailview.c
@@ -282,6 +282,14 @@ format_body(long int msgno, BODY *body,
if((flgs & FM_DISPLAY)
&& !(flgs & FM_NOCOLOR)
&& pico_usingcolor()
+ && ps_global->VAR_SPECIAL_TEXT_FORE_COLOR
+ && ps_global->VAR_SPECIAL_TEXT_BACK_COLOR){
+ gf_link_filter(gf_line_test, gf_line_test_opt(color_this_text, NULL));
+ }
+
+ if((flgs & FM_DISPLAY)
+ && !(flgs & FM_NOCOLOR)
+ && pico_usingcolor()
&& ps_global->VAR_SIGNATURE_FORE_COLOR
&& ps_global->VAR_SIGNATURE_BACK_COLOR){
gf_link_filter(gf_line_test, gf_line_test_opt(color_signature, &is_in_sig));
@@ -2503,6 +2511,190 @@ hdr_color(char *fieldname, char *value,
return(color_pair);
}
+void
+interval_free(IVAL_S **ival)
+{
+ if (!(*ival))
+ return;
+
+ if ((*ival)->next)
+ interval_free(&((*ival)->next));
+
+ fs_give((void **)(ival));
+}
+
+IVAL_S *
+compute_interval (char *string, int endm)
+{
+ IVAL_S *ival = NULL;
+ regmatch_t pmatch;
+
+ if(ps_global->paterror == 0 &&
+ regexec(&ps_global->colorpat, string + endm, 1, &pmatch, 0) == 0){
+ ival = (IVAL_S *) fs_get(sizeof(IVAL_S));
+ ival->start = endm + pmatch.rm_so;
+ ival->end = endm + pmatch.rm_eo;
+ ival->next = compute_interval(string, ival->end);
+ }
+ return ival;
+}
+
+void
+regex_pattern(char **plist)
+{
+ int i = 0, j = 0, len = 0;
+ char *pattern = NULL;
+ regex_t preg;
+
+ if(ps_global->paterror == 0)
+ regfree(&ps_global->colorpat);
+
+ if(plist && *plist && *plist){
+ for (i = 0; plist[i] && plist[i][0]; i++)
+ len += strlen(plist[i]) + 1;
+ pattern = (char *) fs_get(len * sizeof(char));
+ *pattern = '\0';
+ for (j = 0; j < i; j++){
+ strcat(pattern, plist[j]);
+ strcat(pattern, (j < i - 1) ? "|" : "");
+ }
+ if ((ps_global->paterror = regcomp(&preg, pattern, REG_EXTENDED)) != 0)
+ regfree(&preg);
+ else
+ ps_global->colorpat = preg;
+ }
+ if(pattern)
+ fs_give((void **)&pattern);
+}
+
+LT_INS_S **
+insert_color_special_text(LT_INS_S **ins, char **p, IVAL_S *ival, int last_end,
+ COLOR_PAIR *col)
+{
+ struct variable *vars = ps_global->vars;
+
+ if (ival){
+ *p += ival->start - last_end;
+ ins = gf_line_test_new_ins(ins, *p, color_embed(col->fg, col->bg),
+ (2 * RGBLEN) + 4);
+ *p += ival->end - ival->start;
+ ins = gf_line_test_new_ins(ins, *p, color_embed(VAR_NORM_FORE_COLOR,
+ VAR_NORM_BACK_COLOR), (2 * RGBLEN) + 4);
+ ins = insert_color_special_text(ins, p, ival->next, ival->end, col);
+ }
+ return ins;
+}
+
+int
+length_color(char *p, int begin_color)
+{
+ int len = 0, done = begin_color ? 0 : -1;
+ char *orig = p;
+
+ while (*p && done <= 0){
+ switch(*p++){
+ case TAG_HANDLE :
+ p += *p + 1;
+ done++;
+ break;
+
+ case TAG_FGCOLOR :
+ case TAG_BGCOLOR :
+ p += RGBLEN;
+ if (!begin_color)
+ done++;
+ break;
+
+ default :
+ break;
+ }
+ }
+ len = p - orig;
+ return len;
+}
+
+int
+any_color_in_string(char *p)
+{
+ int rv = 0;
+ char *orig = p;
+ while (*p && !rv)
+ if (*p++ == TAG_EMBED)
+ rv = p - orig;
+ return rv;
+}
+
+void
+remove_spaces_ival(IVAL_S **ivalp, char *p)
+{
+ IVAL_S *ival;
+ int i;
+ if (!ivalp || !*ivalp)
+ return;
+ ival = *ivalp;
+ for (i = 0; isspace((unsigned char) p[ival->start + i]); i++);
+ if (ival->start + i < ival->end) /* do not do this if match only spaces */
+ ival->start += i;
+ else
+ return;
+ for (i = 0; isspace((unsigned char) p[ival->end - i - 1]); i++);
+ ival->end -= i;
+ if (ival->next)
+ remove_spaces_ival(&(ival->next), p);
+}
+
+int
+color_this_text(long linenum, char *line, LT_INS_S **ins, void *local)
+{
+ struct variable *vars = ps_global->vars;
+ COLOR_PAIR *col = NULL;
+ char *p;
+ int i = 0;
+ static char *pattern = NULL;
+
+/* select_quote(linenum, line, ins, (void *) &i);
+ for (i = 0; tmp_20k_buf[i] != '\0'; i++); */
+ p = line + i;
+
+ if(VAR_SPECIAL_TEXT_FORE_COLOR && VAR_SPECIAL_TEXT_BACK_COLOR
+ && (col = new_color_pair(VAR_SPECIAL_TEXT_FORE_COLOR,
+ VAR_SPECIAL_TEXT_BACK_COLOR))
+ && !pico_is_good_colorpair(col))
+ free_color_pair(&col);
+
+ if(ps_global->VAR_SPECIAL_TEXT && *ps_global->VAR_SPECIAL_TEXT
+ && **ps_global->VAR_SPECIAL_TEXT && col){
+ IVAL_S *ival;
+ int done = 0, begin_color = 0;
+
+ while (!done){
+ if (i = any_color_in_string(p)){
+ begin_color = (begin_color + 1) % 2;
+ if (begin_color){
+ p[i - 1] = '\0';
+ ival = compute_interval(p, 0);
+ remove_spaces_ival(&ival, p);
+ p[i - 1] = TAG_EMBED;
+ ins = insert_color_special_text(ins, &p, ival, 0, col);
+ }
+ for (;*p++ != TAG_EMBED; );
+ p += length_color(p, begin_color);
+ }
+ else{
+ ival = compute_interval(p, 0);
+ remove_spaces_ival(&ival, p);
+ ins = insert_color_special_text(ins, &p, ival, 0, col);
+ done++;
+ }
+ interval_free(&ival);
+ if (!*p)
+ done++;
+ }
+ free_color_pair(&col);
+ }
+
+ return 0;
+}
/*
* The argument fieldname is something like "Subject:..." or "Subject".
Index: alpine-2.11/pith/mailview.h
===================================================================
--- alpine-2.11.orig/pith/mailview.h
+++ alpine-2.11/pith/mailview.h
@@ -30,6 +30,12 @@
#include "../pith/color.h"
+typedef struct IVAL {
+ int start;
+ int end;
+ struct IVAL *next;
+} IVAL_S;
+
/* format_message flags */
#define FM_DISPLAY 0x0001 /* result is headed for display */
#define FM_NEW_MESS 0x0002 /* a new message so zero out attachment descrip */
@@ -126,6 +132,15 @@ char *format_body(long int, BODY *, HAND
int url_hilite(long, char *, LT_INS_S **, void *);
int handle_start_color(char *, size_t, int *, int);
int handle_end_color(char *, size_t, int *);
+IVAL_S *compute_interval(char *, int);
+void remove_spaces_ival(IVAL_S **, char *);
+void interval_free(IVAL_S **);
+void regex_pattern(char **);
+LT_INS_S **insert_color_special_text(LT_INS_S **, char **, IVAL_S *,
+ int, COLOR_PAIR *);
+int any_color_in_string(char *);
+int length_color(char *, int);
+int color_this_text(long, char *, LT_INS_S **, void *);
/*
* BUG: BELOW IS UNIX/PC ONLY since config'd browser means nothing to webpine
Index: alpine-2.11/pith/pine.hlp
===================================================================
--- alpine-2.11.orig/pith/pine.hlp
+++ alpine-2.11/pith/pine.hlp
@@ -3563,6 +3563,7 @@ There are also additional details on
<li><a href="h_config_print_cat">OPTION: <!--#echo var="VAR_personal-print-category"--></a>
<li><a href="h_config_print_command">OPTION: <!--#echo var="VAR_personal-print-command"--></a>
<li><a href="h_config_post_char_set">OPTION: <!--#echo var="VAR_posting-character-set"--></a>
+<li><a href="h_config_special_text_to_color">OPTION: <!--#echo var="VAR_h_config_special_text_to_color"--></a>
<li><a href="h_config_postponed_folder">OPTION: <!--#echo var="VAR_postponed-folder"--></a>
<li><a href="h_config_print_font_char_set">OPTION: Print-Font-Char-Set</a>
<li><a href="h_config_print_font_name">OPTION: Print-Font-Name</a>
@@ -3591,6 +3592,7 @@ There are also additional details on
<li><a href="h_config_sending_filter">OPTION: <!--#echo var="VAR_sending-filters"--></a>
<li><a href="h_config_sendmail_path">OPTION: <!--#echo var="VAR_sendmail-path"--></a>
<li><a href="h_config_signature_color">OPTION: Signature Color</a>
+<li><a href="h_config_special_text_color">OPTION: Special Text Color</a>
<li><a href="h_config_signature_file">OPTION: <!--#echo var="VAR_signature-file"--></a>
<li><a href="h_config_smtp_server">OPTION: <!--#echo var="VAR_smtp-server"--></a>
<li><a href="h_config_sort_key">OPTION: <!--#echo var="VAR_sort-key"--></a>
@@ -22838,6 +22840,43 @@ That won't work because spell works in a
&lt;End of help on this topic&gt;
</BODY>
</HTML>
+====== h_config_special_text_to_color =====
+<HTML>
+<HEAD>
+<TITLE>OPTION: <!--#echo var="VAR_special-text-color"--></TITLE>
+</HEAD>
+<BODY>
+<H1>OPTION: <!--#echo var="VAR_special-text-color"--></H1>
+
+Use this option to enter patterns (text or regular expressions) that
+Alpine will highlight in the body of the text that is not part of a handle
+(an internal or external link that Alpine paints in a different color).
+
+<P>
+Enter each pattern in a different line. Pine will internally merge these
+patterns (by adding a "|" character), or you can add them all in one line
+by separating them by a "|" character. There is only a <A
+HREF="h_regex_text">set</A> of regular expressions that are matched.
+
+<P>
+Pine will use the colors defined in the
+<A HREF="h_config_special_text_color">Special Text Color</A> variable.
+to paint any match.
+
+<P>
+If the Special Text Color is not set, setting this variable will not
+cause that special text to be indicated in any special way. It will look
+like any normal text. You must set those colors in order to make Pine
+paint the screen differently when it finds the patterns specified in this
+variable.
+
+<P>
+<UL>
+<LI><A HREF="h_finding_help">Finding more information and requesting help</A>
+</UL><P>
+&lt;End of help on this topic&gt;
+</BODY>
+</HTML>
====== h_config_display_filters =====
<HTML>
<HEAD>
@@ -31455,6 +31494,30 @@ the Quote3 Color is black characters on
<P>
<A HREF="h_color_setup">Descriptions of the available commands</A>
<P>
+Look <A HREF="h_edit_nav_cmds">here</A>
+to see the available Editing and Navigation commands.
+<P>
+&lt;End of help on this topic&gt;
+</BODY>
+</HTML>
+====== h_config_special_text_color =====
+<HTML>
+<HEAD>
+<TITLE>OPTION: Special Text Color</TITLE>
+</HEAD>
+<BODY>
+<H1>OPTION: Special Text Color</H1>
+
+Sets the color Pine uses for coloring any text in the body of the message
+that is not part of a handle (and internal or external link that Pine
+paints in a different color). By default, this variable is not defined,
+which means that text that matches the pattern is not painted in any
+particular way. This variable must be set in a special form if you
+want text to be painted.
+
+<P>
+<A HREF="h_color_setup">Descriptions of the available commands</A>
+<P>
Look <A HREF="h_edit_nav_cmds">here</A>
to see the available Editing and Navigation commands.
<P>
Index: alpine-2.11/pith/state.c
===================================================================
--- alpine-2.11.orig/pith/state.c
+++ alpine-2.11/pith/state.c
@@ -131,6 +131,9 @@ free_pine_struct(struct pine **pps)
if((*pps)->folders_dir != NULL)
fs_give((void **)&(*pps)->folders_dir);
+ if((*pps)->paterror == 0)
+ regfree(&(*pps)->colorpat);
+
if((*pps)->ui.homedir)
fs_give((void **)&(*pps)->ui.homedir);
Index: alpine-2.11/pith/state.h
===================================================================
--- alpine-2.11.orig/pith/state.h
+++ alpine-2.11/pith/state.h
@@ -326,6 +326,8 @@ struct pine {
char *display_charmap; /* needs to be freed */
char *keyboard_charmap; /* needs to be freed */
void *input_cs;
+ regex_t colorpat;
+ int paterror;
char *posting_charmap; /* needs to be freed */
Index: alpine-2.11/pith/text.c
===================================================================
--- alpine-2.11.orig/pith/text.c
+++ alpine-2.11/pith/text.c
@@ -171,6 +171,15 @@ decode_text(ATTACH_S *att,
gf_url_hilite_opt(&uh,handlesp,0));
}
+ if((flags & FM_DISPLAY)
+ && !(flags & FM_NOCOLOR)
+ && pico_usingcolor()
+ && VAR_SPECIAL_TEXT_FORE_COLOR
+ && VAR_SPECIAL_TEXT_BACK_COLOR){
+ filters[filtcnt].filter = gf_line_test;
+ filters[filtcnt++].data = gf_line_test_opt(color_this_text, NULL);
+ }
+
/*
* First, paint the signature.
* Disclaimers noted below for coloring quotes apply here as well.