React.js中如何动态匹配数据库数据加载对应音频文件
动态匹配数据库数据播放音频文件的解决方案
问题背景
需要基于数据库返回的数据数组,从文件夹中动态匹配并加载音频文件,但手动导入固定文件名的方式无法满足动态匹配需求,因此要实现遍历数据数组、自动匹配对应音频的功能。
修复后的完整代码
将音频文件移至public目录,并修复audioPlay函数后,实现了动态匹配功能,完整代码如下:
import axios from 'axios' import React, { useEffect, useState } from 'react' import { useLocation } from 'react-router' import api from '../../../Api' import Carregando from '../../../components/Carregando' import OffCanvas from '../../../components/OffCanvas' const audioFilesContext = require.context( '../../../../public/audios/listening-reading', true, /\.mp3$/ ); const ListeningReading = () => { const [play, setPlay] = useState('') const location = useLocation() const conteudoAtual = { nivel: location.state.nivel, aula: location.state.aula } const [posts, setPosts] = useState([]) const [loading, setLoading] = useState(false) useEffect(() =>{ const fetchPost = async () =>{ setLoading(true) await axios.post(`${api}/listening-reading`,{ nivel: conteudoAtual.nivel, aula: conteudoAtual.aula, }).then((response) => { console.log('response') setPosts(response.data) }).catch((rejected)=> { console.error(rejected.response.data)}) setLoading(false) } fetchPost() },[conteudoAtual.nivel, conteudoAtual.aula]) const audioPlay = async () =>{ await posts.map((post) => { const path = audioFilesContext.keys().find((key) => key.replace('./', '') === post.audio) const audioFile = path ? `../../../../public/audios/listening-reading/${path.replace('./', '')}` : null const audioCut = audioFile.replace('../../../../public', '') setPlay(audioCut) }) } if(play === ''){audioPlay()} return ( <> <OffCanvas/> <br/> <div className='container mt-5'> <h1>Listening Reading</h1> { posts.map((post) =>( <div key={post.id}> <h3>{post.titulo}</h3> <p className="fw-semibold">{post.texto}</p> <audio controls> <source src={play} type="audio/mp3" /> Your browser does not support the audio element. </audio> </div> )) } {loading && <Carregando/>} </div> </> ) } export default ListeningReading
此前的固定导入方式(仅支持静态文件名)
这两种方式只能加载固定文件名的音频,无法实现动态匹配:
- 手动ES6导入:
import listenToAudio from '../../../audios/listening-reading/hello.mp3' - 使用
require导入:const listenToAudio = require('../../../audios/listening-reading/hello.mp3')
动态匹配音频的有效实现
现在通过遍历数据库返回的posts数组,每个条目都能匹配到对应的音频文件并播放,核心渲染代码如下:
{ posts.map((post) =>( <div key={post.id}> <h3>{post.titulo}</h3> <p className="fw-semibold">{post.texto}</p> <audio controls> <source src={play} type="audio/mp3" /> Your browser does not support the audio element. </audio> </div> )) }
内容的提问来源于stack exchange,提问作者Felipe Teixeira Schefer
相关产品推荐
相关产品推荐

