import { isImage } from '@/lib/url'
import { useContentPolicy } from '@/providers/ContentPolicyProvider'
import { useEffect, useMemo, useState } from 'react'
import AudioPlayer from '../AudioPlayer'
import VideoPlayer from '../VideoPlayer'
import ExternalLink from '../ExternalLink'
import LazyMediaTapPlaceholder from './LazyMediaTapPlaceholder'
export default function MediaPlayer({
src,
className,
mustLoad = false,
poster,
blurHash
}: {
src: string
className?: string
mustLoad?: boolean
poster?: string
/** NIP-94 / imeta blurhash for lazy placeholder when poster is missing */
blurHash?: string
}) {
const { autoLoadMedia } = useContentPolicy()
const [display, setDisplay] = useState(autoLoadMedia)
const [mediaType, setMediaType] = useState<'video' | 'audio' | null>(null)
// imeta `thumb` / `image` are sometimes the same .mp4 as `url` —
cannot use that, and it
// would hide the blurhash placeholder in LazyMediaTapPlaceholder.
const imagePoster = useMemo(() => {
const p = poster?.trim()
if (!p) return undefined
return isImage(p) ? p : undefined
}, [poster])
useEffect(() => {
if (autoLoadMedia) {
setDisplay(true)
} else {
setDisplay(false)
}
}, [autoLoadMedia])
useEffect(() => {
if (!mustLoad && !display) {
setMediaType(null)
return
}
if (!src) {
setMediaType(null)
return
}
const url = new URL(src)
const extension = url.pathname.split('.').pop()?.toLowerCase()
if (
extension &&
['mp3', 'wav', 'flac', 'aac', 'm4a', 'opus', 'wma', 'mka'].includes(extension)
) {
setMediaType('audio')
return
}
if (extension === 'mkv' || extension === 'ogv') {
setMediaType('video')
return
}
const video = document.createElement('video')
video.src = src
video.preload = 'metadata'
video.onloadedmetadata = () => {
setMediaType(video.videoWidth > 0 || video.videoHeight > 0 ? 'video' : 'audio')
}
video.onerror = () => {
setMediaType(null)
}
return () => {
video.src = ''
}
}, [src, display, mustLoad])
if (!mustLoad && !display) {
return (
setDisplay(true)}
className={className}
/>
)
}
if (!mediaType) {
return
}
if (mediaType === 'video') {
return
}
return
}