courrier clean 2

This commit is contained in:
alma 2025-04-26 18:22:02 +02:00
parent 8137b42c5f
commit ddf72cc4f0

View File

@ -220,6 +220,20 @@ function isLegacyProps(props: ComposeEmailAllProps): props is LegacyComposeEmail
return 'showCompose' in props && 'setShowCompose' in props; return 'showCompose' in props && 'setShowCompose' in props;
} }
// Create a utility function to preprocess email content
function preprocessEmailContent(content: string): string {
if (!content) return '';
// Sanitize HTML content
const sanitized = DOMPurify.sanitize(content);
// Fix common RTL/LTR issues by ensuring consistent direction
// Wrap content in a div with explicit direction if needed
const processed = sanitized.replace(/<div dir=(["'])rtl\1/g, '<div dir="ltr"');
return processed;
}
export default function ComposeEmail(props: ComposeEmailAllProps) { export default function ComposeEmail(props: ComposeEmailAllProps) {
// Handle legacy props by adapting them to new component // Handle legacy props by adapting them to new component
if (isLegacyProps(props)) { if (isLegacyProps(props)) {
@ -282,20 +296,23 @@ export default function ComposeEmail(props: ComposeEmailAllProps) {
? new Date(initialEmail.date).toLocaleString() ? new Date(initialEmail.date).toLocaleString()
: initialEmail.date.toLocaleString(); : initialEmail.date.toLocaleString();
const originalContent = initialEmail.content || initialEmail.html || initialEmail.text || ''; // Preprocess original content to avoid direction issues
const originalContent = preprocessEmailContent(
initialEmail.content || initialEmail.html || initialEmail.text || ''
);
formattedContent = ` formattedContent = `
<br><br> <br><br>
<div style="border-top: 1px solid #ccc; margin-top: 20px; padding-top: 10px;"> <div style="border-top: 1px solid #ccc; margin-top: 20px; padding-top: 10px; direction: ltr; text-align: left;">
<div style="font-family: Arial, sans-serif; color: #333;"> <div style="font-family: Arial, sans-serif; color: #333;">
<div style="margin-bottom: 15px;"> <div style="margin-bottom: 15px;">
<div>---------- Forwarded message ---------</div> <div style="direction: ltr; text-align: left;">---------- Forwarded message ---------</div>
<div><b>From:</b> ${fromString}</div> <div style="direction: ltr; text-align: left;"><b>From:</b> ${fromString}</div>
<div><b>Date:</b> ${dateString}</div> <div style="direction: ltr; text-align: left;"><b>Date:</b> ${dateString}</div>
<div><b>Subject:</b> ${initialEmail.subject || ''}</div> <div style="direction: ltr; text-align: left;"><b>Subject:</b> ${initialEmail.subject || ''}</div>
<div><b>To:</b> ${toString}</div> <div style="direction: ltr; text-align: left;"><b>To:</b> ${toString}</div>
</div> </div>
<div>${originalContent}</div> <div style="direction: ltr; text-align: left;">${originalContent}</div>
</div> </div>
</div> </div>
`; `;
@ -312,11 +329,12 @@ export default function ComposeEmail(props: ComposeEmailAllProps) {
setSubject(formattedEmail.subject); setSubject(formattedEmail.subject);
// Set the reply content with proper formatting // Process content to fix direction issues
formattedContent = formattedEmail.body; formattedContent = preprocessEmailContent(formattedEmail.body);
} }
// Set the entire content as one editable area // Set the entire content as one editable area
// Force LTR direction for quoted content
setBody(formattedContent); setBody(formattedContent);
setUserMessage(formattedContent); setUserMessage(formattedContent);
@ -324,20 +342,27 @@ export default function ComposeEmail(props: ComposeEmailAllProps) {
setTimeout(() => { setTimeout(() => {
if (editorRef.current) { if (editorRef.current) {
editorRef.current.focus(); editorRef.current.focus();
editorRef.current.dir = isRTL ? 'rtl' : 'ltr';
// Place cursor at the beginning of the content // Place cursor at the beginning of the content
const selection = window.getSelection(); const selection = window.getSelection();
const range = document.createRange(); if (selection) {
const range = document.createRange();
range.setStart(editorRef.current, 0);
range.collapse(true); // Find the first text node or element node
let firstNode = editorRef.current.firstChild;
selection?.removeAllRanges(); if (firstNode) {
selection?.addRange(range); range.setStart(firstNode, 0);
range.collapse(true);
selection.removeAllRanges();
selection.addRange(range);
}
}
} }
}, 100); }, 100);
} }
}, [initialEmail, type]); }, [initialEmail, type, isRTL]);
// Format date for the forwarded message header // Format date for the forwarded message header
const formatDate = (date: Date | null): string => { const formatDate = (date: Date | null): string => {
@ -649,13 +674,15 @@ export default function ComposeEmail(props: ComposeEmailAllProps) {
<div className="flex items-center justify-between"> <div className="flex items-center justify-between">
<label htmlFor="body" className="text-sm font-medium">Message</label> <label htmlFor="body" className="text-sm font-medium">Message</label>
<Button <Button
variant="ghost" variant="outline"
size="sm" size="sm"
onClick={toggleTextDirection} onClick={toggleTextDirection}
className="h-8 px-2 text-xs" className="h-8 px-3 text-xs"
> >
{isRTL ? <AlignLeft className="h-4 w-4 mr-1" /> : <AlignRight className="h-4 w-4 mr-1" />} {isRTL ?
{isRTL ? 'LTR' : 'RTL'} <><AlignLeft className="h-4 w-4 mr-1" /> Switch to LTR</> :
<><AlignRight className="h-4 w-4 mr-1" /> Switch to RTL</>
}
</Button> </Button>
</div> </div>
@ -667,8 +694,8 @@ export default function ComposeEmail(props: ComposeEmailAllProps) {
className="w-full p-4 min-h-[300px] focus:outline-none" className="w-full p-4 min-h-[300px] focus:outline-none"
onInput={handleEditorInput} onInput={handleEditorInput}
dangerouslySetInnerHTML={{ __html: DOMPurify.sanitize(body) }} dangerouslySetInnerHTML={{ __html: DOMPurify.sanitize(body) }}
dir={isRTL ? 'rtl' : 'ltr'}
style={{ style={{
direction: isRTL ? 'rtl' : 'ltr',
textAlign: isRTL ? 'right' : 'left' textAlign: isRTL ? 'right' : 'left'
}} }}
/> />