diff --git a/components/email/email-viewer.tsx b/components/email/email-viewer.tsx index 89d53511..30b2150f 100644 --- a/components/email/email-viewer.tsx +++ b/components/email/email-viewer.tsx @@ -2681,6 +2681,22 @@ export function EmailViewer({ restoreBlockedContent(); }, [allowExternalContent, senderIsTrustedNow, hasBlockedContent, restoreBlockedContent]); + // Tracks the last rendered body height so the loading skeleton can hold + // the same size — avoids the body shrink/expand flash when switching emails. + const lastBodyHeightRef = useRef(300); + + // True while the new email's body is still being fetched. Catches the + // window between selectedEmail changing and isLoading flipping true, so the + // quick reply / body don't flicker through a partial render. + const isBodyLoading = isLoading || !email?.bodyValues || Object.keys(email.bodyValues).length === 0; + + // Gates the quick reply on the iframe having loaded the current srcDoc, so + // it doesn't flash in below a still-resizing iframe. + const [iframeReady, setIframeReady] = useState(false); + useLayoutEffect(() => { + setIframeReady(false); + }, [emailIframeSrcDoc]); + const handleIframeLoad = useCallback(() => { const iframe = iframeRef.current; if (!iframe) return; @@ -2691,9 +2707,13 @@ export function EmailViewer({ const resizeObserver = new ResizeObserver(() => { const height = doc.documentElement.scrollHeight; iframe.style.height = height + 'px'; + lastBodyHeightRef.current = height; }); resizeObserver.observe(doc.body); - iframe.style.height = doc.documentElement.scrollHeight + 'px'; + const initialHeight = doc.documentElement.scrollHeight; + iframe.style.height = initialHeight + 'px'; + lastBodyHeightRef.current = initialHeight; + setIframeReady(true); // Make links open in new tab doc.querySelectorAll('a').forEach(a => { @@ -3789,7 +3809,7 @@ export function EmailViewer({ )} {/* Email Content Area */} -
+
{/* === SENDER INFO (Desktop) === */}
@@ -4689,7 +4709,18 @@ export function EmailViewer({ {/* Email Body */}
- {effectiveEmailContent.isHtml ? ( + {isBodyLoading ? ( +
+
+
+
+
+
+
+ ) : effectiveEmailContent.isHtml ? (