feat(reader): integrate TTS controls in ContentPanel

This commit is contained in:
Gigi
2025-10-20 21:41:31 +02:00
parent 34f44c59b5
commit b3206d5e79

View File

@@ -46,6 +46,7 @@ import {
loadReadingPosition,
saveReadingPosition
} from '../services/readingPositionService'
import TTSControls from './TTSControls'
interface ContentPanelProps {
loading: boolean
@@ -321,6 +322,25 @@ const ContentPanel: React.FC<ContentPanelProps> = ({
const hasHighlights = relevantHighlights.length > 0
// Extract plain text for TTS
const baseHtml = useMemo(() => {
if (markdown) return renderedMarkdownHtml && finalHtml ? finalHtml : ''
return finalHtml || html || ''
}, [markdown, renderedMarkdownHtml, finalHtml, html])
const articleText = useMemo(() => {
const parts: string[] = []
if (title) parts.push(title)
if (summary) parts.push(summary)
if (baseHtml) {
const div = document.createElement('div')
div.innerHTML = baseHtml
const txt = (div.textContent || '').replace(/\s+/g, ' ').trim()
if (txt) parts.push(txt)
}
return parts.join('. ')
}, [title, summary, baseHtml])
// Determine if we're on a nostr-native article (/a/) or external URL (/r/)
const isNostrArticle = selectedUrl && selectedUrl.startsWith('nostr:')
const isExternalVideo = !isNostrArticle && !!selectedUrl && ['youtube', 'video'].includes(classifyUrl(selectedUrl).type)
@@ -759,6 +779,11 @@ const ContentPanel: React.FC<ContentPanelProps> = ({
highlights={relevantHighlights}
highlightVisibility={highlightVisibility}
/>
{isTextContent && articleText && (
<div style={{ padding: '0 0.75rem 0.5rem 0.75rem' }}>
<TTSControls text={articleText} defaultLang={navigator?.language} />
</div>
)}
{isExternalVideo ? (
<>
<div className="reader-video">