Fix tts audition (#4637)

Co-authored-by: luowei <glpat-EjySCyNjWiLqAED-YmwM>
Co-authored-by: crazywoola <427733928@qq.com>
Co-authored-by: crazywoola <100913391+crazywoola@users.noreply.github.com>
This commit is contained in:
Charlie.Wei 2024-05-25 12:55:04 +08:00 committed by GitHub
parent 026175c8f7
commit 5bd432a85f
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
7 changed files with 41 additions and 20 deletions

View File

@ -375,6 +375,7 @@ const Answer: FC<IAnswerProps> = ({
<div className='mx-1 w-[1px] h-[14px] bg-gray-200'/>
<AudioBtn
value={content}
noCache={false}
className={cn(s.playBtn)}
/>
</>

View File

@ -41,13 +41,14 @@ const TextToSpeech: FC = () => {
<AudioBtn
value={languageInfo?.example}
voice={voiceItem?.value}
isAudition={true}
isAudition
noCache
/>
)}
</div>
}
noBodySpacing
isShowTextToSpeech={true}
isShowTextToSpeech
/>
)
}

View File

@ -422,6 +422,7 @@ const GenerationItem: FC<IGenerationItemProps> = ({
<div className='ml-2 mr-2 h-[14px] w-[1px] bg-gray-200'></div>
<AudioBtn
value={content}
noCache={false}
className={'mr-1'}
/>
</>

View File

@ -78,6 +78,7 @@ const SavedItems: FC<ISavedItemsProps> = ({
<div className='ml-2 mr-2 h-[14px] w-[1px] bg-gray-200'></div>
<AudioBtn
value={answer}
noCache={false}
className={'mr-1'}
/>
</>

View File

@ -13,6 +13,7 @@ type AudioBtnProps = {
voice?: string
className?: string
isAudition?: boolean
noCache: boolean
}
type AudioState = 'initial' | 'loading' | 'playing' | 'paused' | 'ended'
@ -22,6 +23,7 @@ const AudioBtn = ({
voice,
className,
isAudition,
noCache,
}: AudioBtnProps) => {
const audioRef = useRef<HTMLAudioElement | null>(null)
const [audioState, setAudioState] = useState<AudioState>('initial')
@ -38,12 +40,12 @@ const AudioBtn = ({
const loadAudio = async () => {
const formData = new FormData()
formData.append('text', removeCodeBlocks(value))
formData.append('voice', removeCodeBlocks(voice))
if (value !== '') {
setAudioState('loading')
formData.append('text', removeCodeBlocks(value))
formData.append('voice', removeCodeBlocks(voice))
let url = ''
let isPublic = false
@ -72,15 +74,16 @@ const AudioBtn = ({
}
}
const handleToggle = () => {
if (audioState === 'initial')
loadAudio()
if (audioRef.current) {
const handleToggle = async () => {
if (audioState === 'initial' || noCache) {
await loadAudio()
}
else if (audioRef.current) {
if (audioState === 'playing') {
audioRef.current.pause()
setAudioState('paused')
}
else if (audioState === 'paused' || audioState === 'ended') {
else {
audioRef.current.play()
setAudioState('playing')
}
@ -89,27 +92,31 @@ const AudioBtn = ({
useEffect(() => {
const currentAudio = audioRef.current
const handleLoading = () => {
setAudioState('loading')
}
const handlePlay = () => {
currentAudio?.play()
setAudioState('playing')
}
const handleEnded = () => {
setAudioState('ended')
}
currentAudio?.addEventListener('progress', handleLoading)
currentAudio?.addEventListener('canplaythrough', handlePlay)
currentAudio?.addEventListener('ended', handleEnded)
return () => {
if (currentAudio) {
currentAudio.removeEventListener('progress', handleLoading)
currentAudio.removeEventListener('canplaythrough', handlePlay)
currentAudio.removeEventListener('ended', handleEnded)
URL.revokeObjectURL(currentAudio.src)
currentAudio.src = ''
}
currentAudio?.removeEventListener('progress', handleLoading)
currentAudio?.removeEventListener('canplaythrough', handlePlay)
currentAudio?.removeEventListener('ended', handleEnded)
URL.revokeObjectURL(currentAudio?.src || '')
currentAudio?.pause()
currentAudio?.setAttribute('src', '')
}
}, [])
@ -131,9 +138,17 @@ const AudioBtn = ({
<button
disabled={audioState === 'loading'}
className={`box-border p-0.5 flex items-center justify-center cursor-pointer ${isAudition || '!p-0 rounded-md bg-white'}`}
onClick={handleToggle}>
{audioState === 'loading' && <div className='w-6 h-6 rounded-md flex items-center justify-center p-2'><Loading /></div>}
{audioState !== 'loading' && <div className={`w-6 h-6 rounded-md ${!isAudition ? 'w-4 h-4 hover:bg-gray-50' : 'hover:bg-gray-50'} ${(audioState === 'playing') ? s.pauseIcon : s.playIcon}`}></div>}
onClick={handleToggle}
>
{audioState === 'loading'
? (
<div className='w-6 h-6 rounded-md flex items-center justify-center p-2'>
<Loading />
</div>
)
: (
<div className={`w-6 h-6 rounded-md ${!isAudition ? 'w-4 h-4 hover:bg-gray-50' : 'hover:bg-gray-50'} ${(audioState === 'playing') ? s.pauseIcon : s.playIcon}`}></div>
)}
</button>
</Tooltip>
<audio ref={audioRef} src='' className='hidden' />

View File

@ -120,6 +120,7 @@ const Operation: FC<OperationProps> = ({
<div className='mx-1 w-[1px] h-[14px] bg-gray-200'/>
<AudioBtn
value={content}
noCache={false}
voice={config?.text_to_speech?.voice}
className='hidden group-hover:block'
/>

View File

@ -47,6 +47,7 @@ const TextToSpeech = ({
{ languageInfo?.example && (
<AudioBtn
value={languageInfo?.example}
noCache={false}
isAudition={true}
/>
)}