fix(email-list): show recipient in Sent and Drafts folders
When viewing the Sent or Drafts mailbox, the list items always displayed the sender (email.from[0]) — which is always the logged-in user — instead of the recipient. This makes it impossible to identify messages by who they were sent to. This change detects the current mailbox role from the store and swaps the displayed person to email.to[0] when the role is 'sent' or 'drafts'. For multi-email threads, participant names are computed from the collected recipients of the thread's emails. Affected components: - EmailListItem (flat list, threading disabled) - SingleEmailItem (single-email thread) - ThreadListItem (multi-email thread header + avatar) This matches the behaviour of Gmail, Outlook, Apple Mail, and every other mainstream mail client.
This commit is contained in:
@@ -32,7 +32,7 @@ interface EmailListItemProps {
|
|||||||
|
|
||||||
export function EmailListItem({ email, selected, onClick, onContextMenu, onToggleStar, onMarkAsRead, onDelete, onArchive, onSetColorTag, onMarkAsSpam }: EmailListItemProps) {
|
export function EmailListItem({ email, selected, onClick, onContextMenu, onToggleStar, onMarkAsRead, onDelete, onArchive, onSetColorTag, onMarkAsSpam }: EmailListItemProps) {
|
||||||
const t = useTranslations('email_viewer');
|
const t = useTranslations('email_viewer');
|
||||||
const { selectedEmailIds, toggleEmailSelection, selectRangeEmails, selectedMailbox, clearSelection } = useEmailStore();
|
const { selectedEmailIds, toggleEmailSelection, selectRangeEmails, selectedMailbox, mailboxes, clearSelection } = useEmailStore();
|
||||||
const showPreview = useSettingsStore((state) => state.showPreview);
|
const showPreview = useSettingsStore((state) => state.showPreview);
|
||||||
const density = useSettingsStore((state) => state.density);
|
const density = useSettingsStore((state) => state.density);
|
||||||
const mailLayout = useSettingsStore((state) => state.mailLayout);
|
const mailLayout = useSettingsStore((state) => state.mailLayout);
|
||||||
@@ -44,7 +44,10 @@ export function EmailListItem({ email, selected, onClick, onContextMenu, onToggl
|
|||||||
const isImportant = email.keywords?.["$important"];
|
const isImportant = email.keywords?.["$important"];
|
||||||
const isAnswered = email.keywords?.$answered;
|
const isAnswered = email.keywords?.$answered;
|
||||||
const isForwarded = email.keywords?.$forwarded;
|
const isForwarded = email.keywords?.$forwarded;
|
||||||
const sender = email.from?.[0];
|
// In Sent/Drafts folders, show recipient instead of sender (which is always "me")
|
||||||
|
const currentMailboxRole = mailboxes.find(mb => mb.id === selectedMailbox)?.role;
|
||||||
|
const showRecipient = currentMailboxRole === 'sent' || currentMailboxRole === 'drafts';
|
||||||
|
const sender = showRecipient ? (email.to?.[0] ?? email.from?.[0]) : email.from?.[0];
|
||||||
const isFocusedMailLayout = mailLayout === 'focus';
|
const isFocusedMailLayout = mailLayout === 'focus';
|
||||||
const inlinePreview = showPreview && email.preview ? ` ${email.preview}` : '';
|
const inlinePreview = showPreview && email.preview ? ` ${email.preview}` : '';
|
||||||
|
|
||||||
|
|||||||
@@ -55,8 +55,11 @@ const SingleEmailItem = React.forwardRef<HTMLDivElement, SingleEmailItemProps>(
|
|||||||
const isStarred = email.keywords?.$flagged;
|
const isStarred = email.keywords?.$flagged;
|
||||||
const isAnswered = email.keywords?.$answered;
|
const isAnswered = email.keywords?.$answered;
|
||||||
const isForwarded = email.keywords?.$forwarded;
|
const isForwarded = email.keywords?.$forwarded;
|
||||||
const sender = email.from?.[0];
|
const { selectedMailbox, mailboxes, selectedEmailIds, toggleEmailSelection, selectRangeEmails, clearSelection } = useEmailStore();
|
||||||
const { selectedMailbox, selectedEmailIds, toggleEmailSelection, selectRangeEmails, clearSelection } = useEmailStore();
|
// In Sent/Drafts folders, show recipient instead of sender (which is always "me")
|
||||||
|
const currentMailboxRole = mailboxes.find(mb => mb.id === selectedMailbox)?.role;
|
||||||
|
const showRecipient = currentMailboxRole === 'sent' || currentMailboxRole === 'drafts';
|
||||||
|
const sender = showRecipient ? (email.to?.[0] ?? email.from?.[0]) : email.from?.[0];
|
||||||
const emailKeywords = useSettingsStore((state) => state.emailKeywords);
|
const emailKeywords = useSettingsStore((state) => state.emailKeywords);
|
||||||
const density = useSettingsStore((state) => state.density);
|
const density = useSettingsStore((state) => state.density);
|
||||||
const mailLayout = useSettingsStore((state) => state.mailLayout);
|
const mailLayout = useSettingsStore((state) => state.mailLayout);
|
||||||
@@ -339,7 +342,16 @@ export const ThreadListItem = React.forwardRef<HTMLDivElement, ThreadListItemPro
|
|||||||
const isFocusedMailLayout = mailLayout === 'focus';
|
const isFocusedMailLayout = mailLayout === 'focus';
|
||||||
const inlinePreview = showPreview && latestEmail.preview ? ` ${latestEmail.preview}` : '';
|
const inlinePreview = showPreview && latestEmail.preview ? ` ${latestEmail.preview}` : '';
|
||||||
|
|
||||||
const { selectedMailbox, selectedEmailIds, toggleEmailSelection, selectRangeEmails, clearSelection } = useEmailStore();
|
const { selectedMailbox, mailboxes, selectedEmailIds, toggleEmailSelection, selectRangeEmails, clearSelection } = useEmailStore();
|
||||||
|
// In Sent/Drafts folders, show recipient instead of sender (which is always "me")
|
||||||
|
const currentMailboxRole = mailboxes.find(mb => mb.id === selectedMailbox)?.role;
|
||||||
|
const showRecipient = currentMailboxRole === 'sent' || currentMailboxRole === 'drafts';
|
||||||
|
const displayNames = showRecipient
|
||||||
|
? Array.from(new Set(
|
||||||
|
thread.emails.flatMap(e => (e.to ?? []).map(r => r.name || r.email.split('@')[0]))
|
||||||
|
)).slice(0, 4)
|
||||||
|
: participantNames;
|
||||||
|
const avatarPerson = showRecipient ? latestEmail.to?.[0] : latestEmail.from?.[0];
|
||||||
|
|
||||||
const { dragHandlers, isDragging: isThreadDragging } = useEmailDrag({
|
const { dragHandlers, isDragging: isThreadDragging } = useEmailDrag({
|
||||||
email: latestEmail,
|
email: latestEmail,
|
||||||
@@ -522,8 +534,8 @@ export const ThreadListItem = React.forwardRef<HTMLDivElement, ThreadListItemPro
|
|||||||
|
|
||||||
{!isFocusedMailLayout && density !== 'extra-compact' && (
|
{!isFocusedMailLayout && density !== 'extra-compact' && (
|
||||||
<Avatar
|
<Avatar
|
||||||
name={latestEmail.from?.[0]?.name}
|
name={avatarPerson?.name}
|
||||||
email={latestEmail.from?.[0]?.email}
|
email={avatarPerson?.email}
|
||||||
size="md"
|
size="md"
|
||||||
className="flex-shrink-0 shadow-sm"
|
className="flex-shrink-0 shadow-sm"
|
||||||
/>
|
/>
|
||||||
@@ -537,7 +549,7 @@ export const ThreadListItem = React.forwardRef<HTMLDivElement, ThreadListItemPro
|
|||||||
'w-32 shrink-0 truncate text-sm lg:w-44',
|
'w-32 shrink-0 truncate text-sm lg:w-44',
|
||||||
hasUnread ? 'font-semibold text-foreground' : 'font-medium text-foreground/80'
|
hasUnread ? 'font-semibold text-foreground' : 'font-medium text-foreground/80'
|
||||||
)}>
|
)}>
|
||||||
{participantNames.join(', ')}
|
{displayNames.join(', ')}
|
||||||
</span>
|
</span>
|
||||||
<span
|
<span
|
||||||
className={cn(
|
className={cn(
|
||||||
@@ -591,7 +603,7 @@ export const ThreadListItem = React.forwardRef<HTMLDivElement, ThreadListItemPro
|
|||||||
? "font-bold text-foreground"
|
? "font-bold text-foreground"
|
||||||
: "font-medium text-muted-foreground"
|
: "font-medium text-muted-foreground"
|
||||||
)}>
|
)}>
|
||||||
{participantNames.join(", ")}
|
{displayNames.join(", ")}
|
||||||
</span>
|
</span>
|
||||||
<span
|
<span
|
||||||
className={cn(
|
className={cn(
|
||||||
|
|||||||
Reference in New Issue
Block a user