I'm working on a web app using React and TypeScript. I made a component called SoundEffect, which takes the sound type as a prop, and plays the mp3 according to its type.
interface ISoundEffectProps {
soundType: string,
// duration?: number, <- want to add this
}
const SoundEffect: React.FunctionComponent<ISoundEffectProps> = (props) => {
const sound = soundSelector(props.soundType)
return (
<div>
<audio src={sound} autoPlay></audio>
</div>
);
};
export default SoundEffect;
soundSelector() takes the soundType as a string and returns an mp3 file. Now, I want to add duration to this, so when this component is rendered, like this:
<SoundEffect soundType="count-down" duration=3000/>
it only plays for 3 seconds and stops. Right now, I have to prepare separate mp3 files for different durations, which seems redundant. I can't add any buttons to this component, so I don't think I can have a component that can fire a function (correct me if I'm wrong). If anyone knows any solution or libraries/packages that would help me solve this issue, then please help me. Thanks
------I'll write a solution in below------
interface ISoundEffectProps {
id: string,
soundType: string,
duration?: number,
}
const SoundEffect: React.FunctionComponent<ISoundEffectProps> = (props) => {
const sound = soundSelector(props.soundType); // "../assets/sounds/example.mp3"
const audio = document.getElementById(props.id) as HTMLAudioElement;
// without "as HTMLAudioElement", audio becomes HTMLElement, which does not have pause() method.
function startTimer(duration: number) {
if (audio != null) { // <- audio.pause() creates uncaught typeerror when audio is null
const interval = setInterval(() => {
audio.pause();
}, duration 1000);
}
}
return (
<div>
<audio autoPlay id={props.id} onPlay={()=> startTimer(props.duration || 10)}>
<source src={sound} type="audio/mp3"/>
</audio>
</div>
);
}
Now, I can call for this component like:
<SoundEffect id="beep_id", soundType="beep", duration={5}/>
This component stops its sound after 5 seconds. If I put duration={10}, it stops after 10 seconds.
You could use set interval to pause the playback after a duration.
function startTimer(duration) {
const interval = setInterval(() => {
audioRef.pause()
}, duration * 1000);
}
...
<audio src={sound} autoPlay onplay={()=> startTimer(duration)}></audio>