index.tsx 1.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344
  1. 'use client'
  2. import useSWR from 'swr'
  3. import React, { type FC } from 'react'
  4. import { useTranslation } from 'react-i18next'
  5. import { useContext } from 'use-context-selector'
  6. import { usePathname } from 'next/navigation'
  7. import Panel from '@/app/components/app/configuration/base/feature-panel'
  8. import { Speaker } from '@/app/components/base/icons/src/vender/solid/mediaAndDevices'
  9. import ConfigContext from '@/context/debug-configuration'
  10. import { languages } from '@/utils/language'
  11. import { fetchAppVoices } from '@/service/apps'
  12. const TextToSpeech: FC = () => {
  13. const { t } = useTranslation()
  14. const {
  15. textToSpeechConfig,
  16. } = useContext(ConfigContext)
  17. const pathname = usePathname()
  18. const matched = pathname.match(/\/app\/([^/]+)/)
  19. const appId = (matched?.length && matched[1]) ? matched[1] : ''
  20. const language = textToSpeechConfig.language
  21. const voiceItems = useSWR({ appId, language }, fetchAppVoices).data
  22. const voiceItem = voiceItems?.find(item => item.value === textToSpeechConfig.voice)
  23. return (
  24. <Panel
  25. title={
  26. <div className='flex items-center gap-2'>
  27. <div>{t('appDebug.feature.textToSpeech.title')}</div>
  28. </div>
  29. }
  30. headerIcon={<Speaker className='w-4 h-4 text-[#7839EE]' />}
  31. headerRight={
  32. <div className='text-xs text-gray-500'>
  33. {languages.find(i => i.value === textToSpeechConfig.language)?.name} - {voiceItem?.name ?? t('appDebug.voice.defaultDisplay')}
  34. </div>
  35. }
  36. noBodySpacing
  37. isShowTextToSpeech={true}
  38. />
  39. )
  40. }
  41. export default React.memo(TextToSpeech)