thread fix
This commit is contained in:
parent
a58ba11566
commit
d0fee5c8f7
6 changed files with 262 additions and 34 deletions
|
|
@ -34,12 +34,12 @@ import RecipientField, { recipientsToPayload } from "./compose/RecipientField";
|
|||
import { useCallback, useEffect, useMemo, useRef, useState } from "react";
|
||||
import { listMailAliases, listOrgMembers, sendEmail } from "../api";
|
||||
import { clearDraft, draftStorageKey } from "../utils/composeDraft";
|
||||
import { plainTextFromEmailHtml } from "../utils/emailReply";
|
||||
|
||||
const EMOJI_SAMPLES = ["😀", "😊", "👍", "🙏", "✅", "🎉", "📎", "📅", "💡", "🔥", "❤️", "😅"];
|
||||
|
||||
function plainTextFromHtml(value) {
|
||||
const doc = new DOMParser().parseFromString(value, "text/html");
|
||||
return (doc.body.textContent || "").replace(/\u00a0/g, " ").trim();
|
||||
return plainTextFromEmailHtml(value);
|
||||
}
|
||||
|
||||
function formatFileSize(bytes) {
|
||||
|
|
@ -195,6 +195,7 @@ export default function ComposeModal({
|
|||
const [notice, setNotice] = useState("");
|
||||
const [warnings, setWarnings] = useState([]);
|
||||
const [showEmoji, setShowEmoji] = useState(false);
|
||||
const [showQuoted, setShowQuoted] = useState(false);
|
||||
const [status, setStatus] = useState({ sending: false, error: "" });
|
||||
const [replyToMessageId, setReplyToMessageId] = useState(null);
|
||||
const [replyAll, setReplyAll] = useState(false);
|
||||
|
|
@ -202,6 +203,7 @@ export default function ComposeModal({
|
|||
const orgDomain = account.company_domain || account.email.split("@")[1];
|
||||
const draftKey = draftStorageKey(windowId || account.id);
|
||||
const bodyEmpty = !plainTextFromHtml(bodyHtml);
|
||||
const hasQuotedHistory = bodyHtml.includes('class="gmail_quote"');
|
||||
|
||||
const signatures = useMemo(() => [
|
||||
{
|
||||
|
|
@ -586,7 +588,7 @@ export default function ComposeModal({
|
|||
)}
|
||||
|
||||
<div
|
||||
className="compose-editor"
|
||||
className={`compose-editor${hasQuotedHistory && !showQuoted ? " quotes-collapsed" : ""}`}
|
||||
ref={editorRef}
|
||||
contentEditable
|
||||
suppressContentEditableWarning
|
||||
|
|
@ -600,6 +602,17 @@ export default function ComposeModal({
|
|||
addFiles(event.dataTransfer.files);
|
||||
}}
|
||||
/>
|
||||
{hasQuotedHistory && (
|
||||
<button
|
||||
type="button"
|
||||
className="compose-quoted-toggle"
|
||||
onClick={() => setShowQuoted((visible) => !visible)}
|
||||
aria-expanded={showQuoted}
|
||||
title={showQuoted ? "Hide trimmed content" : "Show trimmed content"}
|
||||
>
|
||||
···
|
||||
</button>
|
||||
)}
|
||||
|
||||
<div className="compose-bottom-stack">
|
||||
<div className="compose-agent-bar compose-agent-bar-disabled" title="AG Agent drafting — coming soon">
|
||||
|
|
|
|||
|
|
@ -44,6 +44,7 @@ import {
|
|||
labelCounts,
|
||||
matchesLens,
|
||||
} from "../utils/inboxSignals";
|
||||
import { buildReplyBodyHtml } from "../utils/emailReply";
|
||||
|
||||
const PAGE_SIZE = 25;
|
||||
const CATEGORY_TABS = [
|
||||
|
|
@ -86,15 +87,12 @@ function buildReplyContext(message, replyAll = false) {
|
|||
const sender = message?.sender || { name: "", address: "" };
|
||||
const subject = (message?.subject || "").trim();
|
||||
const replySubject = /^re:/i.test(subject) ? subject : `Re: ${subject || "(No subject)"}`;
|
||||
const quote = (message?.new_reply_content || message?.body_text || message?.snippet || "").trim();
|
||||
return {
|
||||
replyToMessageId: message.id,
|
||||
replyAll,
|
||||
to: replyAll ? [] : [{ email: sender.address, name: sender.name }],
|
||||
subject: replySubject,
|
||||
bodyHtml: quote
|
||||
? `<p><br></p><blockquote>${quote.replace(/\n/g, "<br>")}</blockquote>`
|
||||
: "<p><br></p>",
|
||||
bodyHtml: buildReplyBodyHtml(message),
|
||||
};
|
||||
}
|
||||
|
||||
|
|
@ -781,7 +779,7 @@ export default function MailboxView({
|
|||
const target = threadDetail?.messages?.[threadDetail.messages.length - 1] || detail;
|
||||
onCompose?.({
|
||||
subject: `Fwd: ${target?.subject || ""}`,
|
||||
bodyHtml: `<p><br></p><blockquote>${(target?.new_reply_content || target?.body_text || target?.snippet || "").replace(/\n/g, "<br>")}</blockquote>`,
|
||||
bodyHtml: buildReplyBodyHtml(target),
|
||||
});
|
||||
}}
|
||||
onExtractActions={() => detail && extractActions(detail)}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue