| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101 |
- import IconMutedVoice from "@/images/icon-muted-voice.png";
- import IconPlay from "@/images/icon-play.png";
- import IconVoiceWave from "@/images/icon-voice-wave.png";
- import { Image, View } from "@tarojs/components";
- import Taro, { useUnload } from "@tarojs/taro";
- import { forwardRef, useImperativeHandle, useState } from "react";
- import style from "./index.module.less";
- import { TVoiceItem } from "@/types/voice";
- interface Props {
- voiceItem?: TVoiceItem | null
- }
- export interface IVoicePlayerBar {
- play: (voice: string) => Promise<void>;
- stop: () => void;
- }
- const audioInstance = Taro.createInnerAudioContext();
- export default forwardRef<IVoicePlayerBar, Props>(({voiceItem}:Props, ref)=> {
- const [playing, setPlaying] = useState(false);
- audioInstance.onEnded(()=> {
- setPlaying(false)
- })
- const stopAudio = ()=> {
- audioInstance.stop()
- setPlaying(false)
- }
- const playVoice = async (voiceUrl: string) => {
- stopAudio();
- try{
- audioInstance.src = voiceUrl
- audioInstance.play()
- setPlaying(true)
- }catch(e){
- setPlaying(false)
- }
- }
- const handlePlay = (voice: string)=> {
- if(!playing && voice){
- playVoice(voice)
- setPlaying(true)
- }
- }
- useImperativeHandle(ref, () => {
- return {
- play: playVoice,
- stop: stopAudio,
- };
- });
- useUnload(()=> {
- stopAudio();
- })
- const renderPlayerBar = () => {
- if (voiceItem) {
- return (
- <>
- <View className={style.playStatus} onClick={()=> handlePlay(voiceItem.voiceUrl)}>
- <Image
- src={playing ? IconVoiceWave : IconPlay}
- mode='widthFix'
- className={style.icon}
- ></Image>
- </View>
- <View className='text-14 leading-22 font-medium truncate'>
- {voiceItem?.voiceName}
- {/* {voiceItem?.gender === 'male' ? "男" : "女"} */}
- </View>
- </>
- );
- }
- // 没有音色的状态
- return (
- <>
- <View className={style.playStatus}>
- <Image
- src={IconMutedVoice}
- mode='widthFix'
- className={style.icon}
- ></Image>
- </View>
- <View className='text-14 leading-22 font-medium text-gray-4'>
- 请选择声音
- </View>
- </>
- );
- };
- return <>
- <View className={style.playerBar}>{renderPlayerBar()}</View>
- </>
- })
|