NeoMutt  2025-12-11-911-gd8d604
Teaching an old dog new tricks
DOXYGEN
Loading...
Searching...
No Matches
functions.c File Reference

Compose functions. More...

#include "config.h"
#include <errno.h>
#include <stdbool.h>
#include <string.h>
#include <sys/stat.h>
#include <unistd.h>
#include "private.h"
#include "mutt/lib.h"
#include "config/lib.h"
#include "email/lib.h"
#include "core/lib.h"
#include "conn/lib.h"
#include "gui/lib.h"
#include "mutt.h"
#include "functions.h"
#include "lib.h"
#include "attach/lib.h"
#include "browser/lib.h"
#include "editor/lib.h"
#include "history/lib.h"
#include "hooks/lib.h"
#include "imap/lib.h"
#include "index/lib.h"
#include "key/lib.h"
#include "menu/lib.h"
#include "ncrypt/lib.h"
#include "nntp/lib.h"
#include "pop/lib.h"
#include "question/lib.h"
#include "send/lib.h"
#include "attach_data.h"
#include "external.h"
#include "globals.h"
#include "module_data.h"
#include "mutt_logging.h"
#include "muttlib.h"
#include "mx.h"
#include "nntp/adata.h"
#include "shared_data.h"
#include <libintl.h>
+ Include dependency graph for functions.c:

Go to the source code of this file.

Functions

void compose_init_keys (struct NeoMutt *n, struct SubMenu *sm_generic)
 Initialise the Compose Keybindings - Implements ::init_keys_api.
 
static bool check_count (struct AttachCtx *actx)
 Check if there are any attachments.
 
static char * gen_cid (void)
 Generate a random Content ID.
 
static bool check_cid (const char *cid)
 Check if a Content-ID is valid.
 
static bool content_id_exists (struct AttachCtx *actx, const struct Body *skip, const char *cid)
 Check whether a Content-ID is already in use.
 
static int check_attachments (struct AttachCtx *actx, struct ConfigSubset *sub)
 Check if any attachments have changed or been deleted.
 
static int delete_attachment (struct AttachCtx *actx, int aidx, struct ConfigSubset *sub)
 Delete an attachment.
 
static void update_idx (struct Menu *menu, struct AttachCtx *actx, struct AttachPtr *ap)
 Add a new attachment to the message.
 
static void compose_attach_swap (struct Email *e, struct AttachCtx *actx, int first, int second)
 Swap two adjacent entries in the attachment list.
 
static int body_index (struct AttachCtx *actx, const struct Body *b)
 Find the index of an attachment body.
 
static int prev_sibling (struct AttachCtx *actx, int index)
 Find the previous sibling of an attachment.
 
static int next_sibling (struct AttachCtx *actx, int index)
 Find the next sibling of an attachment.
 
static bool body_array_contains (struct BodyArray *ba, const struct Body *b)
 Does a selection contain a body?
 
static bool selected_attachments_are_siblings (struct Email *e, struct BodyArray *ba)
 Check whether selected attachments are siblings.
 
static MenuRedrawFlags selection_redraw_flags (size_t count)
 Choose redraw flags for a selection.
 
static int move_attachment (struct ComposeSharedData *shared, bool up, int count)
 Move attachments in the attachment list.
 
static int group_attachments (struct ComposeSharedData *shared, char *subtype, struct BodyArray *ba)
 Group selected attachments into a multipart group.
 
static int op_attach_attach_file (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Attach files to this message - Implements compose_function_t -.
 
static int op_attach_attach_key (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Attach a PGP public key - Implements compose_function_t -.
 
static int op_attach_attach_message (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Attach messages to this message - Implements compose_function_t -.
 
static int op_attach_detach (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Delete the current entry - Implements compose_function_t -.
 
static int op_attach_edit_content_id (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Edit the 'Content-ID' of the attachment - Implements compose_function_t -.
 
static int op_attach_edit_description (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Edit attachment description - Implements compose_function_t -.
 
static int op_attach_edit_encoding (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Edit attachment transfer-encoding - Implements compose_function_t -.
 
static int op_attach_edit_language (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Edit the 'Content-Language' of the attachment - Implements compose_function_t -.
 
static int op_attach_edit_mime (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Edit attachment using mailcap entry - Implements compose_function_t -.
 
static int op_attach_edit_type (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Edit attachment content type - Implements compose_function_t -.
 
static int op_attach_filter (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Filter attachment through a shell command - Implements compose_function_t -.
 
static int op_attach_get_attachment (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Get a temporary copy of an attachment - Implements compose_function_t -.
 
static int op_attach_group_alts (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Group selected attachments as 'multipart/alternative' - Implements compose_function_t -.
 
static int op_attach_group_lingual (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Group selected attachments as 'multipart/multilingual' - Implements compose_function_t -.
 
static int op_attach_group_related (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Group selected attachments as 'multipart/related' - Implements compose_function_t -.
 
static int op_attach_move_down (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Move an attachment down in the attachment list - Implements compose_function_t -.
 
static int op_attach_move_up (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Move an attachment up in the attachment list - Implements compose_function_t -.
 
static int op_attach_new_mime (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Compose new attachment using mailcap entry - Implements compose_function_t -.
 
static int op_attach_print (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Print the current entry - Implements compose_function_t -.
 
static int op_attach_rename_attachment (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Send attachment with a different name - Implements compose_function_t -.
 
static int op_attach_save (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Save message/attachment to a mailbox/file - Implements compose_function_t -.
 
static int op_attach_toggle_disposition (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Toggle disposition between inline/attachment - Implements compose_function_t -.
 
static int op_attach_toggle_recode (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Toggle recoding of this attachment - Implements compose_function_t -.
 
static int op_attach_toggle_unlink (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Toggle whether to delete file after sending it - Implements compose_function_t -.
 
static int op_attach_ungroup (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Ungroup a 'multipart' attachment - Implements compose_function_t -.
 
static int op_attach_update_encoding (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Update an attachment's encoding info - Implements compose_function_t -.
 
static int op_envelope_edit_headers (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Edit the message with headers - Implements compose_function_t -.
 
static int op_compose_edit_file (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Edit the file to be attached - Implements compose_function_t -.
 
static int op_compose_edit_message (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Edit the message - Implements compose_function_t -.
 
static int op_compose_ispell (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Run ispell on the message - Implements compose_function_t -.
 
static int op_compose_postpone_message (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Save this message to send later - Implements compose_function_t -.
 
static int op_compose_rename_file (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Rename/move an attached file - Implements compose_function_t -.
 
static int op_compose_send_message (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Send the message - Implements compose_function_t -.
 
static int op_compose_write_message (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Write the message to a folder - Implements compose_function_t -.
 
static int op_display_headers (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Display message and toggle header weeding - Implements compose_function_t -.
 
static int op_exit (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Exit this menu - Implements compose_function_t -.
 
static int op_forget_passphrase (struct ComposeFunctionData *fdata, const struct KeyEvent *event)
 Wipe passphrases from memory - Implements compose_function_t -.
 
int compose_function_dispatcher (struct MuttWindow *win, const struct KeyEvent *event)
 Perform a Compose function - Implements function_dispatcher_t -.
 

Variables

static const struct MenuFuncOp OpCompose []
 Functions for the Compose Menu.
 
static const struct MenuOpSeq ComposeDefaultBindings []
 Key bindings for the Compose Menu.
 
static const struct ComposeFunction ComposeFunctions []
 All the NeoMutt functions that the Compose supports.
 

Detailed Description

Compose functions.

Authors
  • Pietro Cerutti
  • Richard Russon
  • David Purton

This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

You should have received a copy of the GNU General Public License along with this program. If not, see http://www.gnu.org/licenses/.

Definition in file functions.c.

Function Documentation

◆ compose_init_keys()

void compose_init_keys ( struct NeoMutt * n,
struct SubMenu * sm_generic )

Initialise the Compose Keybindings - Implements ::init_keys_api.

Definition at line 209 of file functions.c.

210{
212 ASSERT(mod_data);
213
214 struct MenuDefinition *md = NULL;
215 struct SubMenu *sm = NULL;
216
218 md = km_register_menu(MENU_COMPOSE, "compose");
219 km_menu_add_submenu(md, sm);
220 km_menu_add_submenu(md, sm_generic);
222
223 mod_data->md_compose = md;
224}
static const struct MenuFuncOp OpCompose[]
Functions for the Compose Menu.
Definition functions.c:78
static const struct MenuOpSeq ComposeDefaultBindings[]
Key bindings for the Compose Menu.
Definition functions.c:146
void km_menu_add_submenu(struct MenuDefinition *md, struct SubMenu *sm)
Add a SubMenu to a Menu Definition.
Definition init.c:121
struct SubMenu * km_register_submenu(const struct MenuFuncOp functions[])
Register a submenu.
Definition init.c:87
struct MenuDefinition * km_register_menu(int menu, const char *name)
Register a menu.
Definition init.c:104
void km_menu_add_bindings(struct MenuDefinition *md, const struct MenuOpSeq bindings[])
Add Keybindings to a Menu.
Definition init.c:134
@ MODULE_ID_COMPOSE
ModuleCompose, Compose an Email
Definition module_api.h:57
void * neomutt_get_module_data(struct NeoMutt *n, enum ModuleId id)
Get the private data for a Module.
Definition neomutt.c:663
#define ASSERT(COND)
Definition signal2.h:59
Compose private Module data.
Definition module_data.h:30
struct MenuDefinition * md_compose
Compose Menu Definition.
Definition module_data.h:32
Functions for a Dialog or Window.
Definition menu.h:77
Collection of related functions.
Definition menu.h:65
@ MENU_COMPOSE
Compose an email.
Definition type.h:40
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ check_count()

static bool check_count ( struct AttachCtx * actx)
static

Check if there are any attachments.

Parameters
actxAttachment context
Return values
trueThere are attachments

Definition at line 231 of file functions.c.

232{
233 if (actx->idxlen == 0)
234 {
235 mutt_error(_("There are no attachments"));
236 return false;
237 }
238
239 return true;
240}
#define mutt_error(...)
Definition logging2.h:94
#define _(a)
Definition message.h:28
short idxlen
Number of attachmentes.
Definition attach.h:70
+ Here is the caller graph for this function:

◆ gen_cid()

static char * gen_cid ( void )
static

Generate a random Content ID.

Return values
ptrContent ID
Note
The caller should free the string

Definition at line 248 of file functions.c.

249{
250 char rndid[MUTT_RANDTAG_LEN + 1];
251
252 mutt_rand_base32(rndid, sizeof(rndid) - 1);
253 rndid[MUTT_RANDTAG_LEN] = 0;
254
255 return mutt_str_dup(rndid);
256}
char * mutt_str_dup(const char *str)
Copy a string, safely.
Definition string.c:257
void mutt_rand_base32(char *buf, size_t buflen)
Fill a buffer with a base32-encoded random string.
Definition random.c:106
#define MUTT_RANDTAG_LEN
Length of random tag for message boundaries.
Definition sendlib.h:36
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ check_cid()

static bool check_cid ( const char * cid)
static

Check if a Content-ID is valid.

Parameters
cidContent-ID to check
Return values
trueContent-ID is valid
falseContent-ID is not valid

Definition at line 264 of file functions.c.

265{
266 static const char *check = "^[-\\.0-9@A-Z_a-z]+$";
267
268 struct Regex *check_cid_regex = mutt_regex_new(check, 0, NULL);
269
270 const bool valid = mutt_regex_match(check_cid_regex, cid);
271
272 mutt_regex_free(&check_cid_regex);
273
274 return valid;
275}
struct Regex * mutt_regex_new(const char *str, uint32_t flags, struct Buffer *err)
Create an Regex from a string.
Definition regex.c:80
void mutt_regex_free(struct Regex **ptr)
Free a Regex object.
Definition regex.c:118
bool mutt_regex_match(const struct Regex *regex, const char *str)
Shorthand to mutt_regex_capture()
Definition regex.c:614
Cached regular expression.
Definition regex3.h:85
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ content_id_exists()

static bool content_id_exists ( struct AttachCtx * actx,
const struct Body * skip,
const char * cid )
static

Check whether a Content-ID is already in use.

Parameters
actxAttachment context
skipBody to ignore
cidContent-ID to check
Return values
trueContent-ID already exists

Definition at line 284 of file functions.c.

285{
286 if (!actx || !cid)
287 return false;
288
289 for (int i = 0; i < actx->idxlen; i++)
290 {
291 struct Body *b = actx->idx[i]->body;
292 if ((b == skip) || !b->content_id)
293 continue;
294
295 if (mutt_str_equal(b->content_id, cid))
296 return true;
297 }
298
299 return false;
300}
bool mutt_str_equal(const char *a, const char *b)
Compare two strings.
Definition string.c:665
struct AttachPtr ** idx
Array of attachments.
Definition attach.h:69
struct Body * body
Attachment.
Definition attach.h:37
The body of an email.
Definition body.h:36
char * content_id
Content-Id (RFC2392)
Definition body.h:58
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ check_attachments()

static int check_attachments ( struct AttachCtx * actx,
struct ConfigSubset * sub )
static

Check if any attachments have changed or been deleted.

Parameters
actxAttachment context
subConfigSubset
Return values
0Success
-1Error

Definition at line 309 of file functions.c.

310{
311 int rc = -1;
312 struct stat st = { 0 };
313 struct Buffer *pretty = NULL, *msg = NULL;
314
315 for (int i = 0; i < actx->idxlen; i++)
316 {
317 if (actx->idx[i]->body->type == TYPE_MULTIPART)
318 continue;
319 if (stat(actx->idx[i]->body->filename, &st) != 0)
320 {
321 if (!pretty)
322 pretty = buf_pool_get();
323 buf_strcpy(pretty, actx->idx[i]->body->filename);
324 pretty_mailbox(pretty);
325 /* L10N: This message is displayed in the compose menu when an attachment
326 doesn't stat. %d is the attachment number and %s is the attachment
327 filename. The filename is located last to avoid a long path hiding
328 the error message. */
329 mutt_error(_("Attachment #%d no longer exists: %s"), i + 1, buf_string(pretty));
330 goto cleanup;
331 }
332
333 if (actx->idx[i]->body->stamp < st.st_mtime)
334 {
335 if (!pretty)
336 pretty = buf_pool_get();
337 buf_strcpy(pretty, actx->idx[i]->body->filename);
338 pretty_mailbox(pretty);
339
340 if (!msg)
341 msg = buf_pool_get();
342 /* L10N: This message is displayed in the compose menu when an attachment
343 is modified behind the scenes. %d is the attachment number and %s is
344 the attachment filename. The filename is located last to avoid a long
345 path hiding the prompt question. */
346 buf_printf(msg, _("Attachment #%d modified. Update encoding for %s?"),
347 i + 1, buf_string(pretty));
348
350 if (ans == MUTT_YES)
351 mutt_update_encoding(actx->idx[i]->body, sub);
352 else if (ans == MUTT_ABORT)
353 goto cleanup;
354 }
355 }
356
357 rc = 0;
358
359cleanup:
360 buf_pool_release(&pretty);
361 buf_pool_release(&msg);
362 return rc;
363}
int buf_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition buffer.c:161
size_t buf_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition buffer.c:395
static const char * buf_string(const struct Buffer *buf)
Convert a buffer to a const char * "string".
Definition buffer.h:96
@ TYPE_MULTIPART
Type: 'multipart/*'.
Definition mime.h:37
void pretty_mailbox(struct Buffer *buf)
Shorten a mailbox path using '~' or '='.
Definition muttlib.c:428
struct Buffer * buf_pool_get(void)
Get a Buffer from the pool.
Definition pool.c:91
void buf_pool_release(struct Buffer **ptr)
Return a Buffer to the pool.
Definition pool.c:111
QuadOption
Possible values for a quad-option.
Definition quad.h:36
@ MUTT_ABORT
User aborted the question (with Ctrl-G)
Definition quad.h:37
@ MUTT_YES
User answered 'Yes', or assume 'Yes'.
Definition quad.h:39
enum QuadOption query_yesorno(const char *prompt, enum QuadOption def)
Ask the user a Yes/No question.
Definition question.c:329
void mutt_update_encoding(struct Body *b, struct ConfigSubset *sub)
Update the encoding type.
Definition sendlib.c:421
time_t stamp
Time stamp of last encoding update.
Definition body.h:77
unsigned int type
content-type primary type, ContentType
Definition body.h:40
char * filename
When sending a message, this is the file to which this structure refers.
Definition body.h:59
String manipulation buffer.
Definition buffer.h:36
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ delete_attachment()

static int delete_attachment ( struct AttachCtx * actx,
int aidx,
struct ConfigSubset * sub )
static

Delete an attachment.

Parameters
actxAttachment context
aidxIndex number of attachment to delete
subConfig subset
Return values
0Success
-1Error

Definition at line 373 of file functions.c.

374{
375 if (!actx || (aidx < 0) || (aidx >= actx->idxlen))
376 return -1;
377
378 struct AttachPtr **idx = actx->idx;
379 struct Body *b_previous = NULL;
380 struct Body *b_parent = NULL;
381
382 if (aidx == 0)
383 {
384 struct Body *b = actx->idx[0]->body;
385 if (!b->next) // There's only one attachment left
386 {
387 mutt_error(_("You may not delete the only attachment"));
388 return -1;
389 }
390
391 if (cs_subset_bool(sub, "compose_confirm_detach_first"))
392 {
393 /* L10N: Prompt when trying to hit <detach-file> on the first entry in
394 the compose menu. This entry is most likely the message they just
395 typed. Hitting yes will remove the entry and unlink the file, so
396 it's worth confirming they really meant to do it. */
397 enum QuadOption ans = query_yesorno_help(_("Really delete the main message?"), MUTT_NO,
398 sub, "compose_confirm_detach_first");
399 if (ans == MUTT_NO)
400 {
401 idx[aidx]->body->tagged = false;
402 return -1;
403 }
404 }
405 }
406
407 if (idx[aidx]->level > 0)
408 {
409 if (attach_body_parent(idx[0]->body, NULL, idx[aidx]->body, &b_parent))
410 {
411 if (attach_body_count(b_parent->parts, false) < 3)
412 {
413 mutt_error(_("Can't leave group with only one attachment"));
414 return -1;
415 }
416 }
417 }
418
419 // reorder body pointers
420 if (aidx > 0)
421 {
422 if (attach_body_previous(idx[0]->body, idx[aidx]->body, &b_previous))
423 b_previous->next = idx[aidx]->body->next;
424 else if (attach_body_parent(idx[0]->body, NULL, idx[aidx]->body, &b_parent))
425 b_parent->parts = idx[aidx]->body->next;
426 }
427
428 // free memory
429 int part_count = 1;
430 if (aidx < (actx->idxlen - 1))
431 {
432 if ((idx[aidx]->body->type == TYPE_MULTIPART) &&
433 (idx[aidx + 1]->level > idx[aidx]->level))
434 {
435 part_count += attach_body_count(idx[aidx]->body->parts, true);
436 }
437 }
438 idx[aidx]->body->next = NULL;
439 mutt_body_free(&(idx[aidx]->body));
440 for (int i = 0; i < part_count; i++)
441 {
442 FREE(&idx[aidx + i]->tree);
443 FREE(&idx[aidx + i]);
444 }
445
446 // reorder attachment list
447 for (int i = aidx; i < (actx->idxlen - part_count); i++)
448 idx[i] = idx[i + part_count];
449 for (int i = 0; i < part_count; i++)
450 idx[actx->idxlen - i - 1] = NULL;
451 actx->idxlen -= part_count;
452
453 return 0;
454}
bool attach_body_parent(struct Body *start, struct Body *start_parent, struct Body *body, struct Body **body_parent)
Find the parent of a body.
Definition lib.c:71
int attach_body_count(struct Body *body, bool recurse)
Count bodies.
Definition lib.c:42
bool attach_body_previous(struct Body *start, struct Body *body, struct Body **previous)
Find the previous body of a body.
Definition lib.c:142
bool cs_subset_bool(const struct ConfigSubset *sub, const char *name)
Get a boolean config item by name.
Definition helpers.c:47
void mutt_body_free(struct Body **ptr)
Free a Body.
Definition body.c:58
#define FREE(x)
Free memory and set the pointer to NULL.
Definition memory.h:68
@ MUTT_NO
User answered 'No', or assume 'No'.
Definition quad.h:38
enum QuadOption query_yesorno_help(const char *prompt, enum QuadOption def, struct ConfigSubset *sub, const char *name)
Ask the user a Yes/No question offering help.
Definition question.c:357
An email to which things will be attached.
Definition attach.h:36
struct Body * parts
parts of a multipart or message/rfc822
Definition body.h:73
bool tagged
This attachment is tagged.
Definition body.h:90
struct Body * next
next attachment in the list
Definition body.h:72
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ update_idx()

static void update_idx ( struct Menu * menu,
struct AttachCtx * actx,
struct AttachPtr * ap )
static

Add a new attachment to the message.

Parameters
menuCurrent menu
actxAttachment context
apAttachment to add

Definition at line 462 of file functions.c.

463{
464 ap->level = 0;
465 for (int i = actx->idxlen; i > 0; i--)
466 {
467 if (ap->level == actx->idx[i - 1]->level)
468 {
469 actx->idx[i - 1]->body->next = ap->body;
470 break;
471 }
472 }
473
474 ap->body->aptr = ap;
475 mutt_actx_add_attach(actx, ap);
476 update_menu(actx, menu, false);
477 menu_set_index(menu, actx->vcount - 1);
478}
void mutt_actx_add_attach(struct AttachCtx *actx, struct AttachPtr *attach)
Add an Attachment to an Attachment Context.
Definition attach.c:65
void update_menu(struct AttachCtx *actx, struct Menu *menu, bool init)
Redraw the compose window.
MenuRedrawFlags menu_set_index(struct Menu *menu, int index)
Set the current selection in the Menu.
Definition menu.c:169
short vcount
The number of virtual attachments.
Definition attach.h:74
int level
Nesting depth of attachment.
Definition attach.h:41
struct AttachPtr * aptr
Menu information, used in recvattach.c.
Definition body.h:75
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ compose_attach_swap()

static void compose_attach_swap ( struct Email * e,
struct AttachCtx * actx,
int first,
int second )
static

Swap two adjacent entries in the attachment list.

Parameters
eEmail
actxAttachment information
firstIndex of first attachment to swap
secondIndex of second attachment to swap

Definition at line 487 of file functions.c.

488{
489 struct AttachPtr **idx = actx->idx;
490
491 // check that attachments really are adjacent
492 if (idx[first]->body->next != idx[second]->body)
493 return;
494
495 // reorder Body pointers
496 if (first == 0)
497 {
498 // first attachment is the fundamental part
499 idx[first]->body->next = idx[second]->body->next;
500 idx[second]->body->next = idx[first]->body;
501 e->body = idx[second]->body;
502 }
503 else
504 {
505 // find previous attachment
506 struct Body *b_previous = NULL;
507 struct Body *b_parent = NULL;
508 if (attach_body_previous(e->body, idx[first]->body, &b_previous))
509 {
510 idx[first]->body->next = idx[second]->body->next;
511 idx[second]->body->next = idx[first]->body;
512 b_previous->next = idx[second]->body;
513 }
514 else if (attach_body_parent(e->body, NULL, idx[first]->body, &b_parent))
515 {
516 idx[first]->body->next = idx[second]->body->next;
517 idx[second]->body->next = idx[first]->body;
518 b_parent->parts = idx[second]->body;
519 }
520 }
521
522 // reorder attachment list
523 struct AttachPtr *saved = idx[second];
524 for (int i = second; i > first; i--)
525 idx[i] = idx[i - 1];
526 idx[first] = saved;
527
528 // if moved attachment is a group then move subparts too
529 if ((idx[first]->body->type == TYPE_MULTIPART) && (second < actx->idxlen - 1))
530 {
531 int i = second + 1;
532 while (idx[i]->level > idx[first]->level)
533 {
534 saved = idx[i];
535 int destidx = i - second + first;
536 for (int j = i; j > destidx; j--)
537 idx[j] = idx[j - 1];
538 idx[destidx] = saved;
539 i++;
540 if (i >= actx->idxlen)
541 break;
542 }
543 }
544}
struct Body * body
List of MIME parts.
Definition email.h:69
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ body_index()

static int body_index ( struct AttachCtx * actx,
const struct Body * b )
static

Find the index of an attachment body.

Parameters
actxAttachment context
bBody to find
Return values
numIndex of body
-1Body wasn't found

Definition at line 553 of file functions.c.

554{
555 if (!actx || !b)
556 return -1;
557
558 for (int i = 0; i < actx->idxlen; i++)
559 {
560 if (actx->idx[i]->body == b)
561 return i;
562 }
563
564 return -1;
565}
+ Here is the caller graph for this function:

◆ prev_sibling()

static int prev_sibling ( struct AttachCtx * actx,
int index )
static

Find the previous sibling of an attachment.

Parameters
actxAttachment context
indexIndex of attachment
Return values
numIndex of previous sibling
-1No previous sibling

Definition at line 574 of file functions.c.

575{
576 if (!actx || (index <= 0) || (index >= actx->idxlen))
577 return -1;
578
579 const int level = actx->idx[index]->level;
580 int previdx = index - 1;
581 while ((previdx > 0) && (actx->idx[previdx]->level > level))
582 previdx--;
583
584 return (actx->idx[previdx]->level == level) ? previdx : -1;
585}
+ Here is the caller graph for this function:

◆ next_sibling()

static int next_sibling ( struct AttachCtx * actx,
int index )
static

Find the next sibling of an attachment.

Parameters
actxAttachment context
indexIndex of attachment
Return values
numIndex of next sibling
-1No next sibling

Definition at line 594 of file functions.c.

595{
596 if (!actx || (index < 0) || (index >= actx->idxlen))
597 return -1;
598
599 const int level = actx->idx[index]->level;
600 int nextidx = index + 1;
601 while ((nextidx < actx->idxlen) && (actx->idx[nextidx]->level > level))
602 nextidx++;
603
604 if ((nextidx >= actx->idxlen) || (actx->idx[nextidx]->level != level))
605 return -1;
606
607 return nextidx;
608}
+ Here is the caller graph for this function:

◆ body_array_contains()

static bool body_array_contains ( struct BodyArray * ba,
const struct Body * b )
static

Does a selection contain a body?

Parameters
baSelected attachments
bBody to find
Return values
trueBody is selected

Definition at line 616 of file functions.c.

617{
618 struct Body **bp = NULL;
619 ARRAY_FOREACH(bp, ba)
620 {
621 if (*bp == b)
622 return true;
623 }
624
625 return false;
626}
#define ARRAY_FOREACH(elem, head)
Iterate over all elements of the array.
Definition array.h:223
+ Here is the caller graph for this function:

◆ selected_attachments_are_siblings()

static bool selected_attachments_are_siblings ( struct Email * e,
struct BodyArray * ba )
static

Check whether selected attachments are siblings.

Parameters
eEmail
baSelected attachments
Return values
trueSelected attachments are siblings

Definition at line 634 of file functions.c.

635{
636 if (!e || !ba)
637 return false;
638
639 int level = -1;
640 struct Body *parent = NULL;
641 struct Body **bp = NULL;
642 ARRAY_FOREACH(bp, ba)
643 {
644 struct Body *this_parent = NULL;
645 struct Body *body = *bp;
646 if (body->aptr && (body->aptr->level > 0))
647 {
648 if (!attach_body_parent(e->body, NULL, body, &this_parent))
649 return false;
650 }
651
652 if (level == -1)
653 {
654 level = body->aptr ? body->aptr->level : 0;
655 parent = this_parent;
656 continue;
657 }
658
659 if ((level != (body->aptr ? body->aptr->level : 0)) || (parent != this_parent))
660 return false;
661 }
662
663 return true;
664}
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ selection_redraw_flags()

static MenuRedrawFlags selection_redraw_flags ( size_t count)
static

Choose redraw flags for a selection.

Parameters
countNumber of selected attachments
Return values
redrawflags for the selection

Definition at line 671 of file functions.c.

672{
673 return (count > 1) ? MENU_REDRAW_FULL : MENU_REDRAW_CURRENT;
674}
@ MENU_REDRAW_FULL
Redraw everything.
Definition lib.h:64
@ MENU_REDRAW_CURRENT
Redraw the current line of the menu.
Definition lib.h:63
+ Here is the caller graph for this function:

◆ move_attachment()

static int move_attachment ( struct ComposeSharedData * shared,
bool up,
int count )
static

Move attachments in the attachment list.

Parameters
sharedShared compose data
upIf true, move up, otherwise move down
countRepeat-count
Return values
enumFunctionRetval

Definition at line 683 of file functions.c.

684{
685 struct AttachCtx *actx = shared->adata->actx;
686 if (!check_count(actx))
687 return FR_ERROR;
688
689 struct Menu *menu = shared->adata->menu;
690 struct AttachPtr *cur_att = current_attachment(actx, menu);
691 if (!cur_att)
692 return FR_ERROR;
693
694 struct Body *cur_body = cur_att->body;
695 struct BodyArray ba = ARRAY_HEAD_INITIALIZER;
696 ba_add_selection(&ba, actx, menu, menu->tag_prefix, count);
697 if (ARRAY_EMPTY(&ba))
698 goto done;
699
700 if ((ARRAY_SIZE(&ba) > 1) && !selected_attachments_are_siblings(shared->email, &ba))
701 {
702 mutt_error(_("Selected attachments must be siblings"));
703 ARRAY_FREE(&ba);
704 return FR_ERROR;
705 }
706
707 bool moved = false;
708 if (up)
709 {
710 struct Body **bp = NULL;
711 ARRAY_FOREACH(bp, &ba)
712 {
713 const int index = body_index(actx, *bp);
714 const int previdx = prev_sibling(actx, index);
715 if (previdx < 0)
716 continue;
717 if (body_array_contains(&ba, actx->idx[previdx]->body))
718 continue;
719
720 compose_attach_swap(shared->email, actx, previdx, index);
721 moved = true;
722 }
723 }
724 else
725 {
726 for (int i = ARRAY_SIZE(&ba) - 1; i >= 0; i--)
727 {
728 struct Body **bp = ARRAY_GET(&ba, i);
729 const int index = body_index(actx, *bp);
730 const int nextidx = next_sibling(actx, index);
731 if (nextidx < 0)
732 continue;
733 if (body_array_contains(&ba, actx->idx[nextidx]->body))
734 continue;
735
736 compose_attach_swap(shared->email, actx, index, nextidx);
737 moved = true;
738 }
739 }
740
741 if (!moved)
742 {
743 mutt_error(up ? _("Attachment is already at top") : _("Attachment is already at bottom"));
744 goto done;
745 }
746
747 mutt_update_tree(actx);
750
751 const int index = body_index(actx, cur_body);
752 if (index >= 0)
753 menu_set_index(menu, index);
754
755 ARRAY_FREE(&ba);
756 return FR_SUCCESS;
757
758done:
759 ARRAY_FREE(&ba);
760 return FR_ERROR;
761}
#define ARRAY_EMPTY(head)
Check if an array is empty.
Definition array.h:74
#define ARRAY_SIZE(head)
The number of elements stored.
Definition array.h:87
#define ARRAY_FREE(head)
Release all memory.
Definition array.h:209
#define ARRAY_GET(head, idx)
Return the element at index.
Definition array.h:109
#define ARRAY_HEAD_INITIALIZER
Static initializer for arrays.
Definition array.h:58
static bool check_count(struct AttachCtx *actx)
Check if there are any attachments.
Definition functions.c:231
static int body_index(struct AttachCtx *actx, const struct Body *b)
Find the index of an attachment body.
Definition functions.c:553
static int prev_sibling(struct AttachCtx *actx, int index)
Find the previous sibling of an attachment.
Definition functions.c:574
static void compose_attach_swap(struct Email *e, struct AttachCtx *actx, int first, int second)
Swap two adjacent entries in the attachment list.
Definition functions.c:487
static bool body_array_contains(struct BodyArray *ba, const struct Body *b)
Does a selection contain a body?
Definition functions.c:616
static int next_sibling(struct AttachCtx *actx, int index)
Find the next sibling of an attachment.
Definition functions.c:594
static bool selected_attachments_are_siblings(struct Email *e, struct BodyArray *ba)
Check whether selected attachments are siblings.
Definition functions.c:634
@ FR_SUCCESS
Valid function - successfully performed.
Definition dispatcher.h:40
@ FR_ERROR
Valid function - error occurred.
Definition dispatcher.h:39
@ NT_EMAIL_CHANGE_ATTACH
Email's Attachments have changed.
Definition email.h:188
void menu_queue_redraw(struct Menu *menu, MenuRedrawFlags redraw)
Queue a request for a redraw.
Definition menu.c:179
@ MENU_REDRAW_INDEX
Redraw the index.
Definition lib.h:61
bool notify_send(struct Notify *notify, enum NotifyType event_type, int event_subtype, void *event_data)
Send out a notification message.
Definition notify.c:173
@ NT_EMAIL
Email has changed, NotifyEmail, EventEmail.
Definition notify_type.h:44
struct AttachPtr * current_attachment(struct AttachCtx *actx, struct Menu *menu)
Get the current attachment.
Definition recvattach.c:71
void mutt_update_tree(struct AttachCtx *actx)
Refresh the list of attachments.
Definition recvattach.c:116
int ba_add_selection(struct BodyArray *ba, struct AttachCtx *actx, struct Menu *menu, bool use_tagged, int count)
Build a working set of attachment bodies for an action.
Definition selection.c:164
A set of attachments.
Definition attach.h:65
struct Menu * menu
Menu displaying the attachments.
Definition attach_data.h:35
struct AttachCtx * actx
Set of attachments.
Definition attach_data.h:34
struct ComposeAttachData * adata
Attachments.
Definition shared_data.h:39
struct Email * email
Email being composed.
Definition shared_data.h:38
struct Notify * notify
Notifications: NotifyEmail, EventEmail.
Definition email.h:73
Definition lib.h:86
bool tag_prefix
User has pressed <tag-prefix>
Definition lib.h:92
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ group_attachments()

static int group_attachments ( struct ComposeSharedData * shared,
char * subtype,
struct BodyArray * ba )
static

Group selected attachments into a multipart group.

Parameters
sharedShared compose data
subtypeMIME subtype
baSelected attachments
Return values
FR_SUCCESSSuccess
FR_ERRORFailure

Definition at line 771 of file functions.c.

773{
774 struct AttachCtx *actx = shared->adata->actx;
775 int group_level = -1;
776 struct Body *bptr_parent = NULL;
777
778 // Attachments to be grouped must have the same parent
779 for (int i = 0; i < actx->idxlen; i++)
780 {
781 if (body_array_contains(ba, actx->idx[i]->body))
782 {
783 if (group_level == -1)
784 {
785 group_level = actx->idx[i]->level;
786 }
787 else
788 {
789 if (group_level != actx->idx[i]->level)
790 {
791 mutt_error(_("Attachments to be grouped must have the same parent"));
792 return FR_ERROR;
793 }
794 }
795 // if not at top level check if all tagged attachments have same parent
796 if (group_level > 0)
797 {
798 if (bptr_parent)
799 {
800 struct Body *bptr_test = NULL;
801 if (!attach_body_parent(actx->idx[0]->body, NULL, actx->idx[i]->body, &bptr_test))
802 mutt_debug(LL_DEBUG5, "can't find parent\n");
803 if (bptr_test != bptr_parent)
804 {
805 mutt_error(_("Attachments to be grouped must have the same parent"));
806 return FR_ERROR;
807 }
808 }
809 else
810 {
811 if (!attach_body_parent(actx->idx[0]->body, NULL, actx->idx[i]->body, &bptr_parent))
812 mutt_debug(LL_DEBUG5, "can't find parent\n");
813 }
814 }
815 }
816 }
817
818 // Can't group all attachments unless at top level
819 if (bptr_parent)
820 {
821 if (ARRAY_SIZE(ba) == attach_body_count(bptr_parent->parts, false))
822 {
823 mutt_error(_("Can't leave group with only one attachment"));
824 return FR_ERROR;
825 }
826 }
827
828 struct Body *group = mutt_body_new();
829 group->type = TYPE_MULTIPART;
830 group->subtype = mutt_str_dup(subtype);
831 group->encoding = ENC_7BIT;
832
833 struct Body *bptr_first = NULL; // first selected attachment
834 struct Body *bptr = NULL; // current selected attachment
835 struct Body *group_parent = NULL; // parent of group
836 struct Body *group_previous = NULL; // previous body to group
837 struct Body *group_part = NULL; // current attachment in group
838 int group_idx = 0; // index in attachment list where group will be inserted
839 int group_last_idx = 0; // index of last part of previous found group
840 int group_parent_type = TYPE_OTHER;
841
842 for (int i = 0; i < actx->idxlen; i++)
843 {
844 bptr = actx->idx[i]->body;
845 if (body_array_contains(ba, bptr))
846 {
847 // set group properties based on first selected attachment
848 if (!bptr_first)
849 {
850 group->disposition = bptr->disposition;
851 if (bptr->language && !mutt_str_equal(subtype, "multilingual"))
852 group->language = mutt_str_dup(bptr->language);
853 group_parent_type = bptr->aptr->parent_type;
854 bptr_first = bptr;
855 if (i > 0)
856 {
857 if (!attach_body_previous(shared->email->body, bptr, &group_previous))
858 {
859 mutt_debug(LL_DEBUG5, "couldn't find previous\n");
860 }
861 if (!attach_body_parent(shared->email->body, NULL, bptr, &group_parent))
862 {
863 mutt_debug(LL_DEBUG5, "couldn't find parent\n");
864 }
865 }
866 }
867
868 if (bptr->tagged)
869 {
870 shared->adata->menu->num_tagged--;
871 bptr->tagged = false;
872 }
873 bptr->aptr->level++;
875
876 // append bptr to the group parts list and remove from email body list
877 struct Body *bptr_previous = NULL;
878 if (attach_body_previous(shared->email->body, bptr, &bptr_previous))
879 bptr_previous->next = bptr->next;
880 else if (attach_body_parent(shared->email->body, NULL, bptr, &bptr_parent))
881 bptr_parent->parts = bptr->next;
882 else
883 shared->email->body = bptr->next;
884
885 if (group_part)
886 {
887 // add bptr to group parts list
888 group_part->next = bptr;
889 group_part = group_part->next;
890 group_part->next = NULL;
891
892 // reorder attachments and set levels
893 int bptr_attachments = attach_body_count(bptr, true);
894 for (int j = i + 1; j < (i + bptr_attachments); j++)
895 actx->idx[j]->level++;
896 if (i > (group_last_idx + 1))
897 {
898 for (int j = 0; j < bptr_attachments; j++)
899 {
900 struct AttachPtr *saved = actx->idx[i + bptr_attachments - 1];
901 for (int k = i + bptr_attachments - 1; k > (group_last_idx + 1); k--)
902 actx->idx[k] = actx->idx[k - 1];
903 actx->idx[group_last_idx + 1] = saved;
904 }
905 }
906 i += bptr_attachments - 1;
907 group_last_idx += bptr_attachments;
908 }
909 else
910 {
911 group_idx = i;
912 group->parts = bptr;
913 group_part = bptr;
914 group_part->next = NULL;
915 int bptr_attachments = attach_body_count(bptr, true);
916 for (int j = i + 1; j < (i + bptr_attachments); j++)
917 actx->idx[j]->level++;
918 i += bptr_attachments - 1;
919 group_last_idx = i;
920 }
921 }
922 }
923
924 if (!bptr_first)
925 {
926 mutt_body_free(&group);
927 return FR_ERROR;
928 }
929
930 // set group->next
931 int next_aidx = group_idx + attach_body_count(group->parts, true);
932 if (group_parent)
933 {
934 // find next attachment with the same parent as the group
935 struct Body *b = NULL;
936 struct Body *b_parent = NULL;
937 while (next_aidx < actx->idxlen)
938 {
939 b = actx->idx[next_aidx]->body;
940 b_parent = NULL;
941 if (attach_body_parent(shared->email->body, NULL, b, &b_parent))
942 {
943 if (group_parent == b_parent)
944 {
945 group->next = b;
946 break;
947 }
948 }
949 next_aidx++;
950 }
951 }
952 else if (next_aidx < actx->idxlen)
953 {
954 // group is at top level
955 group->next = actx->idx[next_aidx]->body;
956 }
957
958 // set previous or parent for group
959 if (group_previous)
960 group_previous->next = group;
961 else if (group_parent)
962 group_parent->parts = group;
963
965
966 struct AttachPtr *group_ap = mutt_aptr_new();
967 group_ap->body = group;
968 group_ap->body->aptr = group_ap;
969 group_ap->level = group_level;
970 group_ap->parent_type = group_parent_type;
971
972 // insert group into attachment list
973 mutt_actx_ins_attach(actx, group_ap, group_idx);
974
975 // update email body and last attachment pointers
976 shared->email->body = actx->idx[0]->body;
977 actx->idx[actx->idxlen - 1]->body->next = NULL;
978
979 update_menu(actx, shared->adata->menu, false);
980 shared->adata->menu->current = group_idx;
982
983 exec_message_hook(NULL, shared->email, CMD_SEND2_HOOK);
984 return FR_SUCCESS;
985}
void mutt_actx_ins_attach(struct AttachCtx *actx, struct AttachPtr *attach, int aidx)
Insert an Attachment into an Attachment Context at Specified Index.
Definition attach.c:91
struct AttachPtr * mutt_aptr_new(void)
Create a new Attachment Pointer.
Definition attach.c:40
@ CMD_SEND2_HOOK
:send2-hook
Definition command.h:109
struct Body * mutt_body_new(void)
Create a new Body.
Definition body.c:44
#define mutt_debug(LEVEL,...)
Definition logging2.h:91
void exec_message_hook(struct Mailbox *m, struct Email *e, enum CommandId id)
Perform a message hook.
Definition exec.c:137
@ LL_DEBUG5
Log at debug level 5.
Definition logging2.h:49
@ ENC_7BIT
7-bit text
Definition mime.h:49
@ TYPE_OTHER
Unknown Content-Type.
Definition mime.h:31
void mutt_generate_boundary(struct ParameterList *pl)
Create a unique boundary id for a MIME part.
Definition multipart.c:93
int parent_type
Type of parent attachment, e.g. TYPE_MULTIPART.
Definition attach.h:39
char * language
content-language (RFC8255)
Definition body.h:78
struct ParameterList parameter
Parameters of the content-type.
Definition body.h:63
unsigned int disposition
content-disposition, ContentDisposition
Definition body.h:42
char * subtype
content-type subtype
Definition body.h:61
unsigned int encoding
content-transfer-encoding, ContentEncoding
Definition body.h:41
int current
Current entry.
Definition lib.h:87
int num_tagged
Number of tagged entries.
Definition lib.h:101
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

Variable Documentation

◆ OpCompose

const struct MenuFuncOp OpCompose[]
static

Functions for the Compose Menu.

Definition at line 78 of file functions.c.

78 { /* map: compose */
79 { "attach-file", OP_ATTACH_ATTACH_FILE },
80 { "attach-key", OP_ATTACH_ATTACH_KEY },
81 { "attach-message", OP_ATTACH_ATTACH_MESSAGE },
82 { "attach-news-message", OP_ATTACH_ATTACH_NEWS_MESSAGE },
83#ifdef USE_AUTOCRYPT
84 { "autocrypt-menu", OP_COMPOSE_AUTOCRYPT_MENU },
85#endif
86 { "copy-file", OP_ATTACH_SAVE },
87 { "detach-file", OP_ATTACH_DETACH },
88 { "display-toggle-weed", OP_DISPLAY_HEADERS },
89 { "edit-bcc", OP_ENVELOPE_EDIT_BCC },
90 { "edit-cc", OP_ENVELOPE_EDIT_CC },
91 { "edit-content-id", OP_ATTACH_EDIT_CONTENT_ID },
92 { "edit-description", OP_ATTACH_EDIT_DESCRIPTION },
93 { "edit-encoding", OP_ATTACH_EDIT_ENCODING },
94 { "edit-fcc", OP_ENVELOPE_EDIT_FCC },
95 { "edit-file", OP_COMPOSE_EDIT_FILE },
96 { "edit-followup-to", OP_ENVELOPE_EDIT_FOLLOWUP_TO },
97 { "edit-from", OP_ENVELOPE_EDIT_FROM },
98 { "edit-headers", OP_ENVELOPE_EDIT_HEADERS },
99 { "edit-language", OP_ATTACH_EDIT_LANGUAGE },
100 { "edit-message", OP_COMPOSE_EDIT_MESSAGE },
101 { "edit-mime", OP_ATTACH_EDIT_MIME },
102 { "edit-newsgroups", OP_ENVELOPE_EDIT_NEWSGROUPS },
103 { "edit-reply-to", OP_ENVELOPE_EDIT_REPLY_TO },
104 { "edit-subject", OP_ENVELOPE_EDIT_SUBJECT },
105 { "edit-to", OP_ENVELOPE_EDIT_TO },
106 { "edit-type", OP_ATTACH_EDIT_TYPE },
107 { "edit-x-comment-to", OP_ENVELOPE_EDIT_X_COMMENT_TO },
108 { "exit", OP_EXIT },
109 { "filter-entry", OP_ATTACH_FILTER },
110 { "forget-passphrase", OP_FORGET_PASSPHRASE },
111 { "get-attachment", OP_ATTACH_GET_ATTACHMENT },
112 { "group-alternatives", OP_ATTACH_GROUP_ALTS },
113 { "group-multilingual", OP_ATTACH_GROUP_LINGUAL },
114 { "group-related", OP_ATTACH_GROUP_RELATED },
115 { "ispell", OP_COMPOSE_ISPELL },
116 { "move-down", OP_ATTACH_MOVE_DOWN },
117 { "move-up", OP_ATTACH_MOVE_UP },
118 { "new-mime", OP_ATTACH_NEW_MIME },
119 { "pgp-menu", OP_COMPOSE_PGP_MENU },
120 { "pipe-entry", OP_PIPE },
121 { "pipe-message", OP_PIPE },
122 { "postpone-message", OP_COMPOSE_POSTPONE_MESSAGE },
123 { "preview-page-down", OP_PREVIEW_PAGE_DOWN },
124 { "preview-page-up", OP_PREVIEW_PAGE_UP },
125 { "print-entry", OP_ATTACH_PRINT },
126 { "rename-attachment", OP_ATTACH_RENAME_ATTACHMENT },
127 { "rename-file", OP_COMPOSE_RENAME_FILE },
128 { "send-message", OP_COMPOSE_SEND_MESSAGE },
129 { "smime-menu", OP_COMPOSE_SMIME_MENU },
130 { "toggle-disposition", OP_ATTACH_TOGGLE_DISPOSITION },
131 { "toggle-recode", OP_ATTACH_TOGGLE_RECODE },
132 { "toggle-unlink", OP_ATTACH_TOGGLE_UNLINK },
133 { "ungroup-attachment", OP_ATTACH_UNGROUP },
134 { "update-encoding", OP_ATTACH_UPDATE_ENCODING },
135 { "view-attach", OP_ATTACH_VIEW },
136 { "view-mailcap", OP_ATTACH_VIEW_MAILCAP },
137 { "view-pager", OP_ATTACH_VIEW_PAGER },
138 { "view-text", OP_ATTACH_VIEW_TEXT },
139 { "write-fcc", OP_COMPOSE_WRITE_MESSAGE },
140 { NULL, 0 },
141};

◆ ComposeDefaultBindings

const struct MenuOpSeq ComposeDefaultBindings[]
static

Key bindings for the Compose Menu.

Definition at line 146 of file functions.c.

146 { /* map: compose */
147 { OP_ATTACH_ATTACH_FILE, "a" },
148 { OP_ATTACH_ATTACH_KEY, "\033k" }, // <Alt-k>
149 { OP_ATTACH_ATTACH_MESSAGE, "A" },
150 { OP_ATTACH_DETACH, "D" },
151 { OP_ATTACH_EDIT_CONTENT_ID, "\033i" }, // <Alt-i>
152 { OP_ATTACH_EDIT_DESCRIPTION, "d" },
153 { OP_ATTACH_EDIT_ENCODING, "\005" }, // <Ctrl-E>
154 { OP_ATTACH_EDIT_LANGUAGE, "\014" }, // <Ctrl-L>
155 { OP_ATTACH_EDIT_MIME, "m" },
156 { OP_ATTACH_EDIT_TYPE, "\024" }, // <Ctrl-T>
157 { OP_ATTACH_FILTER, "F" },
158 { OP_ATTACH_GET_ATTACHMENT, "G" },
159 { OP_ATTACH_GROUP_ALTS, "&" },
160 { OP_ATTACH_GROUP_LINGUAL, "^" },
161 { OP_ATTACH_GROUP_RELATED, "%" },
162 { OP_ATTACH_MOVE_DOWN, "+" },
163 { OP_ATTACH_MOVE_UP, "-" },
164 { OP_ATTACH_NEW_MIME, "n" },
165 { OP_EXIT, "q" },
166 { OP_PIPE, "|" },
167 { OP_ATTACH_PRINT, "l" },
168 { OP_ATTACH_RENAME_ATTACHMENT, "\017" }, // <Ctrl-O>
169 { OP_ATTACH_SAVE, "C" },
170 { OP_ATTACH_TOGGLE_DISPOSITION, "\004" }, // <Ctrl-D>
171 { OP_ATTACH_TOGGLE_UNLINK, "u" },
172 { OP_ATTACH_UNGROUP, "#" },
173 { OP_ATTACH_UPDATE_ENCODING, "U" },
174 { OP_ATTACH_VIEW, "<keypadenter>" },
175 { OP_ATTACH_VIEW, "\n" }, // <Enter>
176 { OP_ATTACH_VIEW, "\r" }, // <Return>
177#ifdef USE_AUTOCRYPT
178 { OP_COMPOSE_AUTOCRYPT_MENU, "o" },
179#endif
180 { OP_COMPOSE_EDIT_FILE, "\033e" }, // <Alt-e>
181 { OP_COMPOSE_EDIT_MESSAGE, "e" },
182 { OP_COMPOSE_ISPELL, "i" },
183 { OP_COMPOSE_PGP_MENU, "p" },
184 { OP_COMPOSE_POSTPONE_MESSAGE, "P" },
185 { OP_COMPOSE_RENAME_FILE, "R" },
186 { OP_COMPOSE_SEND_MESSAGE, "y" },
187 { OP_COMPOSE_SMIME_MENU, "S" },
188 { OP_COMPOSE_WRITE_MESSAGE, "w" },
189 { OP_DISPLAY_HEADERS, "h" },
190 { OP_ENVELOPE_EDIT_BCC, "b" },
191 { OP_ENVELOPE_EDIT_CC, "c" },
192 { OP_ENVELOPE_EDIT_FCC, "f" },
193 { OP_ENVELOPE_EDIT_FROM, "\033f" }, // <Alt-f>
194 { OP_ENVELOPE_EDIT_HEADERS, "E" },
195 { OP_ENVELOPE_EDIT_REPLY_TO, "r" },
196 { OP_ENVELOPE_EDIT_SUBJECT, "s" },
197 { OP_ENVELOPE_EDIT_TO, "t" },
198 { OP_PREVIEW_PAGE_DOWN, "<pagedown>" },
199 { OP_PREVIEW_PAGE_UP, "<pageup>" },
200 { OP_FORGET_PASSPHRASE, "\006" }, // <Ctrl-F>
201 { OP_TAG, "T" },
202 { 0, NULL },
203};

◆ ComposeFunctions

const struct ComposeFunction ComposeFunctions[]
static

All the NeoMutt functions that the Compose supports.

Definition at line 2661 of file functions.c.

2661 {
2662 // clang-format off
2663 { OP_ATTACH_ATTACH_FILE, op_attach_attach_file },
2664 { OP_ATTACH_ATTACH_KEY, op_attach_attach_key },
2665 { OP_ATTACH_ATTACH_MESSAGE, op_attach_attach_message },
2666 { OP_ATTACH_ATTACH_NEWS_MESSAGE, op_attach_attach_message },
2667 { OP_ATTACH_DETACH, op_attach_detach },
2668 { OP_ATTACH_EDIT_CONTENT_ID, op_attach_edit_content_id },
2669 { OP_ATTACH_EDIT_DESCRIPTION, op_attach_edit_description },
2670 { OP_ATTACH_EDIT_ENCODING, op_attach_edit_encoding },
2671 { OP_ATTACH_EDIT_LANGUAGE, op_attach_edit_language },
2672 { OP_ATTACH_EDIT_MIME, op_attach_edit_mime },
2673 { OP_ATTACH_EDIT_TYPE, op_attach_edit_type },
2674 { OP_ATTACH_FILTER, op_attach_filter },
2675 { OP_ATTACH_GET_ATTACHMENT, op_attach_get_attachment },
2676 { OP_ATTACH_GROUP_ALTS, op_attach_group_alts },
2677 { OP_ATTACH_GROUP_LINGUAL, op_attach_group_lingual },
2678 { OP_ATTACH_GROUP_RELATED, op_attach_group_related },
2679 { OP_ATTACH_MOVE_DOWN, op_attach_move_down },
2680 { OP_ATTACH_MOVE_UP, op_attach_move_up },
2681 { OP_ATTACH_NEW_MIME, op_attach_new_mime },
2682 { OP_ATTACH_PRINT, op_attach_print },
2683 { OP_ATTACH_RENAME_ATTACHMENT, op_attach_rename_attachment },
2684 { OP_ATTACH_SAVE, op_attach_save },
2685 { OP_ATTACH_TOGGLE_DISPOSITION, op_attach_toggle_disposition },
2686 { OP_ATTACH_TOGGLE_RECODE, op_attach_toggle_recode },
2687 { OP_ATTACH_TOGGLE_UNLINK, op_attach_toggle_unlink },
2688 { OP_ATTACH_UNGROUP, op_attach_ungroup },
2689 { OP_ATTACH_UPDATE_ENCODING, op_attach_update_encoding },
2690 { OP_ATTACH_VIEW, op_display_headers },
2691 { OP_ATTACH_VIEW_MAILCAP, op_display_headers },
2692 { OP_ATTACH_VIEW_PAGER, op_display_headers },
2693 { OP_ATTACH_VIEW_TEXT, op_display_headers },
2694 { OP_COMPOSE_EDIT_FILE, op_compose_edit_file },
2695 { OP_COMPOSE_EDIT_MESSAGE, op_compose_edit_message },
2696 { OP_COMPOSE_ISPELL, op_compose_ispell },
2697 { OP_COMPOSE_POSTPONE_MESSAGE, op_compose_postpone_message },
2698 { OP_COMPOSE_RENAME_FILE, op_compose_rename_file },
2699 { OP_COMPOSE_SEND_MESSAGE, op_compose_send_message },
2700 { OP_COMPOSE_WRITE_MESSAGE, op_compose_write_message },
2701 { OP_DISPLAY_HEADERS, op_display_headers },
2702 { OP_ENVELOPE_EDIT_HEADERS, op_envelope_edit_headers },
2703 { OP_EXIT, op_exit },
2704 { OP_FORGET_PASSPHRASE, op_forget_passphrase },
2705 { OP_PIPE, op_attach_filter },
2706 { 0, NULL },
2707 // clang-format on
2708};
static int op_exit(struct AliasFunctionData *fdata, const struct KeyEvent *event)
exit this menu - Implements alias_function_t -
Definition functions.c:312
static int op_attach_edit_type(struct AttachFunctionData *fdata, const struct KeyEvent *event)
edit attachment content type - Implements attach_function_t -
Definition functions.c:393
static int op_attach_save(struct AttachFunctionData *fdata, const struct KeyEvent *event)
save message/attachment to a mailbox/file - Implements attach_function_t -
Definition functions.c:430
static int op_attach_print(struct AttachFunctionData *fdata, const struct KeyEvent *event)
print the current entry - Implements attach_function_t -
Definition functions.c:417
static int op_forget_passphrase(struct AttachFunctionData *fdata, const struct KeyEvent *event)
wipe passphrases from memory - Implements attach_function_t -
Definition functions.c:644
static int op_attach_edit_description(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Edit attachment description - Implements compose_function_t -.
Definition functions.c:1412
static int op_compose_postpone_message(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Save this message to send later - Implements compose_function_t -.
Definition functions.c:2424
static int op_attach_edit_content_id(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Edit the 'Content-ID' of the attachment - Implements compose_function_t -.
Definition functions.c:1327
static int op_attach_group_lingual(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Group selected attachments as 'multipart/multilingual' - Implements compose_function_t -.
Definition functions.c:1736
static int op_compose_write_message(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Write the message to a folder - Implements compose_function_t -.
Definition functions.c:2521
static int op_compose_edit_message(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Edit the message - Implements compose_function_t -.
Definition functions.c:2374
static int op_attach_ungroup(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Ungroup a 'multipart' attachment - Implements compose_function_t -.
Definition functions.c:2200
static int op_compose_ispell(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Run ispell on the message - Implements compose_function_t -.
Definition functions.c:2398
static int op_attach_update_encoding(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Update an attachment's encoding info - Implements compose_function_t -.
Definition functions.c:2263
static int op_attach_get_attachment(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Get a temporary copy of an attachment - Implements compose_function_t -.
Definition functions.c:1672
static int op_attach_group_related(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Group selected attachments as 'multipart/related' - Implements compose_function_t -.
Definition functions.c:1777
static int op_compose_rename_file(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Rename/move an attached file - Implements compose_function_t -.
Definition functions.c:2441
static int op_attach_move_up(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Move an attachment up in the attachment list - Implements compose_function_t -.
Definition functions.c:1872
static int op_attach_filter(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Filter attachment through a shell command - Implements compose_function_t -.
Definition functions.c:1636
static int op_attach_edit_language(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Edit the 'Content-Language' of the attachment - Implements compose_function_t -.
Definition functions.c:1520
static int op_attach_toggle_disposition(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Toggle disposition between inline/attachment - Implements compose_function_t -.
Definition functions.c:2085
static int op_attach_rename_attachment(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Send attachment with a different name - Implements compose_function_t -.
Definition functions.c:2024
static int op_attach_move_down(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Move an attachment down in the attachment list - Implements compose_function_t -.
Definition functions.c:1812
static int op_attach_group_alts(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Group selected attachments as 'multipart/alternative' - Implements compose_function_t -.
Definition functions.c:1715
static int op_attach_attach_key(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Attach a PGP public key - Implements compose_function_t -.
Definition functions.c:1058
static int op_attach_toggle_recode(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Toggle recoding of this attachment - Implements compose_function_t -.
Definition functions.c:2117
static int op_envelope_edit_headers(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Edit the message with headers - Implements compose_function_t -.
Definition functions.c:2299
static int op_compose_send_message(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Send the message - Implements compose_function_t -.
Definition functions.c:2492
static int op_attach_edit_encoding(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Edit attachment transfer-encoding - Implements compose_function_t -.
Definition functions.c:1460
static int op_attach_toggle_unlink(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Toggle whether to delete file after sending it - Implements compose_function_t -.
Definition functions.c:2169
static int op_attach_detach(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Delete the current entry - Implements compose_function_t -.
Definition functions.c:1240
static int op_display_headers(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Display message and toggle header weeding - Implements compose_function_t -.
Definition functions.c:2565
static int op_attach_attach_message(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Attach messages to this message - Implements compose_function_t -.
Definition functions.c:1087
static int op_compose_edit_file(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Edit the file to be attached - Implements compose_function_t -.
Definition functions.c:2349
static int op_attach_edit_mime(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Edit attachment using mailcap entry - Implements compose_function_t -.
Definition functions.c:1573
static int op_attach_new_mime(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Compose new attachment using mailcap entry - Implements compose_function_t -.
Definition functions.c:1911
static int op_attach_attach_file(struct ComposeFunctionData *fdata, const struct KeyEvent *event)
Attach files to this message - Implements compose_function_t -.
Definition functions.c:992