diff -Pur mutt/OPS mutt-patch/OPS --- mutt/OPS Mon Oct 10 11:21:18 2005 +++ mutt-patch/OPS Sat May 6 05:47:31 2006 @@ -56,6 +56,7 @@ OP_DISPLAY_ADDRESS "display full address of sender" OP_DISPLAY_HEADERS "display message and toggle header weeding" OP_DISPLAY_MESSAGE "display a message" +OP_EDIT_LABEL "add, change, or delete a message's label" OP_EDIT_MESSAGE "edit the raw message" OP_EDITOR_BACKSPACE "delete the char in front of the cursor" OP_EDITOR_BACKWARD_CHAR "move the cursor one character to the left" diff -Pur mutt/PATCHES mutt-patch/PATCHES --- mutt/PATCHES Wed Dec 31 18:00:00 1969 +++ mutt-patch/PATCHES Sat May 6 05:48:28 2006 @@ -1,0 +1 @@ +patch-1.5.11.dgc.xlabel_ext.8 diff -Pur mutt/copy.c mutt-patch/copy.c --- mutt/copy.c Tue Jan 10 11:34:44 2006 +++ mutt-patch/copy.c Sat May 6 05:48:28 2006 @@ -108,6 +108,10 @@ ignore = 0; } + if (flags & CH_UPDATE_LABEL && + mutt_strncasecmp ("X-Label:", buf, 8) == 0) + continue; + if (!ignore && fputs (buf, out) == EOF) return (-1); } @@ -475,6 +479,15 @@ fprintf (out, "Lines: %d\n", h->lines); } + if (flags & CH_UPDATE_LABEL && h->xlabel_changed) + { + h->xlabel_changed = 0; + if (h->env->x_label != NULL) + if (fprintf(out, "X-Label: %s\n", h->env->x_label) != + 10 + strlen(h->env->x_label)) + return -1; + } + if ((flags & CH_NONEWLINE) == 0) { if (flags & CH_PREFIX) @@ -555,6 +568,9 @@ else _mutt_make_string (prefix, sizeof (prefix), NONULL (Prefix), Context, hdr, 0); } + + if (hdr->xlabel_changed) + chflags |= CH_UPDATE_LABEL; if ((flags & M_CM_NOHEADER) == 0) { diff -Pur mutt/curs_main.c mutt-patch/curs_main.c --- mutt/curs_main.c Fri Apr 28 10:39:33 2006 +++ mutt-patch/curs_main.c Sat May 6 05:48:28 2006 @@ -1926,6 +1926,21 @@ menu->redraw = REDRAW_FULL; break; + case OP_EDIT_LABEL: + + CHECK_MSGCOUNT; + CHECK_READONLY; + rc = mutt_label_message(tag ? NULL : CURHDR); + if (rc > 0) { + Context->changed = 1; + menu->redraw = REDRAW_FULL; + mutt_message ("%d label%s changed.", rc, rc == 1 ? "" : "s"); + } + else { + mutt_message _("No labels changed."); + } + break; + case OP_LIST_REPLY: CHECK_ATTACH; diff -Pur mutt/doc/manual.xml.head mutt-patch/doc/manual.xml.head --- mutt/doc/manual.xml.head Fri May 5 14:11:57 2006 +++ mutt-patch/doc/manual.xml.head Sat May 6 05:49:09 2006 @@ -4020,6 +4020,12 @@ +You can change or delete the ``X-Label:'' field within Mutt using the +``edit-label'' command, bound to the ``y'' key by default. This works +for tagged messages, too. + + + Lastly, Mutt has the ability to sort the mailbox into threads. A thread is a group of messages which all relate to the same subject. This is usually organized into a tree-like structure where a diff -Pur mutt/functions.h mutt-patch/functions.h --- mutt/functions.h Mon Oct 10 11:21:24 2005 +++ mutt-patch/functions.h Sat May 6 05:48:28 2006 @@ -82,6 +82,7 @@ { "delete-thread", OP_DELETE_THREAD, "\004" }, { "delete-subthread", OP_DELETE_SUBTHREAD, "\033d" }, { "edit", OP_EDIT_MESSAGE, "e" }, + { "edit-label", OP_EDIT_LABEL, "y" }, { "edit-type", OP_EDIT_TYPE, "\005" }, { "forward-message", OP_FORWARD_MESSAGE, "f" }, { "flag-message", OP_FLAG_MESSAGE, "F" }, @@ -166,6 +167,7 @@ { "delete-thread", OP_DELETE_THREAD, "\004" }, { "delete-subthread", OP_DELETE_SUBTHREAD, "\033d" }, { "edit", OP_EDIT_MESSAGE, "e" }, + { "edit-label", OP_EDIT_LABEL, "y" }, { "edit-type", OP_EDIT_TYPE, "\005" }, { "forward-message", OP_FORWARD_MESSAGE, "f" }, { "flag-message", OP_FLAG_MESSAGE, "F" }, diff -Pur mutt/headers.c mutt-patch/headers.c --- mutt/headers.c Fri Apr 28 10:39:33 2006 +++ mutt-patch/headers.c Sat May 6 06:12:02 2006 @@ -205,3 +205,59 @@ } } } + +/* + * dgc: Add an X-Label: field. + */ +static int label_message(HEADER *hdr, char *new) +{ + if (hdr == NULL) + return 0; + if (hdr->env->x_label == NULL && new == NULL) + return 0; + if (hdr->env->x_label != NULL && new != NULL && + strcmp(hdr->env->x_label, new) == 0) + return 0; + if (hdr->env->x_label != NULL) + FREE(&hdr->env->x_label); + if (new == NULL) + hdr->env->x_label = NULL; + else + hdr->env->x_label = safe_strdup(new); + return hdr->changed = hdr->xlabel_changed = 1; +} + +int mutt_label_message(HEADER *hdr) +{ + char buf[LONG_STRING], *new; + int i; + int changed; + + *buf = '\0'; + if (hdr != NULL && hdr->env->x_label != NULL) { + strncpy(buf, hdr->env->x_label, LONG_STRING); + } + + mutt_get_field("Label: ", buf, sizeof(buf), 0 /* | M_CLEAR */); + new = buf; + SKIPWS(new); + if (*new == '\0') + new = NULL; + + changed = 0; + if (hdr != NULL) { + changed += label_message(hdr, new); + } else { +#define HDR_OF(index) Context->hdrs[Context->v2r[(index)]] + for (i = 0; i < Context->vcount; ++i) { + if (HDR_OF(i)->tagged) + if (label_message(HDR_OF(i), new)) { + ++changed; + mutt_set_flag(Context, HDR_OF(i), + M_TAG, 0); + } + } + } + + return changed; +} diff -Pur mutt/imap/imap.c mutt-patch/imap/imap.c --- mutt/imap/imap.c Fri Apr 28 10:39:36 2006 +++ mutt-patch/imap/imap.c Sat May 6 06:05:48 2006 @@ -1158,7 +1158,7 @@ * we delete the message and reupload it. * This works better if we're expunging, of course. */ if ((h->env && (h->env->refs_changed || h->env->irt_changed)) || - h->attach_del) + h->attach_del || h->xlabel_changed) { mutt_message (_("Saving changed messages... [%d/%d]"), n+1, ctx->msgcount); @@ -1170,6 +1170,7 @@ } else _mutt_save_message (h, appendctx, 1, 0, 0); + h->xlabel_changed = 0; } } } diff -Pur mutt/imap/message.c mutt-patch/imap/message.c --- mutt/imap/message.c Fri Apr 28 10:39:36 2006 +++ mutt-patch/imap/message.c Sat May 6 05:45:22 2006 @@ -360,6 +360,7 @@ IMAP_CACHE *cache; int read; int rc; + char *x_label = NULL; /* Sam's weird courier server returns an OK response even when FETCH * fails. Thanks Sam. */ short fetched = 0; diff -Pur mutt/mh.c mutt-patch/mh.c --- mutt/mh.c Fri Apr 28 10:39:34 2006 +++ mutt-patch/mh.c Sat May 6 05:48:28 2006 @@ -1390,7 +1390,7 @@ { HEADER *h = ctx->hdrs[msgno]; - if (h->attach_del || + if (h->attach_del || h->xlabel_changed || (h->env && (h->env->refs_changed || h->env->irt_changed))) if (mh_rewrite_message (ctx, msgno) != 0) return -1; @@ -1402,7 +1402,7 @@ { HEADER *h = ctx->hdrs[msgno]; - if (h->attach_del || + if (h->attach_del || h->xlabel_changed || (h->env && (h->env->refs_changed || h->env->irt_changed))) { /* when doing attachment deletion/rethreading, fall back to the MH case. */ @@ -1511,6 +1511,7 @@ } } else if (ctx->hdrs[i]->changed || ctx->hdrs[i]->attach_del || + ctx->hdrs[i]->xlabel_changed || (ctx->magic == M_MAILDIR && (option (OPTMAILDIRTRASH) || ctx->hdrs[i]->trash) && (ctx->hdrs[i]->deleted != ctx->hdrs[i]->trash))) diff -Pur mutt/mutt.h mutt-patch/mutt.h --- mutt/mutt.h Fri May 5 14:11:56 2006 +++ mutt-patch/mutt.h Sat May 6 05:49:20 2006 @@ -92,6 +92,7 @@ #define CH_NOQFROM (1<<15) /* give CH_FROM precedence over CH_WEED? */ #define CH_UPDATE_IRT (1<<16) /* update In-Reply-To: */ #define CH_UPDATE_REFS (1<<17) /* update References: */ +#define CH_UPDATE_LABEL (1<<18) /* update X-Label: from hdr->env->x_label? */ /* flags for mutt_enter_string() */ #define M_ALIAS 1 /* do alias "completion" by calling up the alias-menu */ @@ -717,6 +718,7 @@ * This flag is used by the maildir_trash * option. */ + unsigned int xlabel_changed : 1; /* editable - used for syncing */ /* timezone of the sender of this message */ unsigned int zhours : 5; diff -Pur mutt/pager.c mutt-patch/pager.c --- mutt/pager.c Tue Jan 10 11:34:48 2006 +++ mutt-patch/pager.c Sat May 6 05:48:28 2006 @@ -2658,6 +2658,18 @@ redraw = REDRAW_FULL; break; + case OP_EDIT_LABEL: + CHECK_MODE(IsHeader (extra)); + rc = mutt_label_message(extra->hdr); + if (rc > 0) { + Context->changed = 1; + redraw = REDRAW_FULL; + mutt_message ("%d label%s changed.", rc, rc == 1 ? "" : "s"); + } + else { + mutt_message _("No labels changed."); + } + break; case OP_MAIL_KEY: if (!(WithCrypto & APPLICATION_PGP)) Binary files mutt/pattern.o and mutt-patch/pattern.o differ diff -Pur mutt/protos.h mutt-patch/protos.h --- mutt/protos.h Fri May 5 14:11:56 2006 +++ mutt-patch/protos.h Sat May 6 05:48:29 2006 @@ -180,6 +180,7 @@ void 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); +int mutt_label_message (HEADER *); void mutt_curses_error (const char *, ...); void mutt_curses_message (const char *, ...); void mutt_enter_command (void);