【问题标题】:How to use ReactHowler with a playlist如何将 ReactHowler 与播放列表一起使用
【发布时间】:2020-08-09 11:59:14
【问题描述】:

我从外部源获取一个播放列表作为 JSON 对象,其中包含曲目的标题,还包含音频文件的 URL。我将此对象映射到带有<ul><li> 元素,但我无法让它工作。我安装了 Howler 和 HowlerReact,但在页面加载时出现以下错误:

  • TypeError:无法读取未定义的属性“长度”
  • Howl.playing
  • node_modules/howler/dist/howler.js:1691

这是我的代码:

import React, { useState } from 'react';
import ReactHowler from 'react-howler'
import Async from 'react-async';

const loadTracks = () =>
    fetch('...')
    .then(res => (res.ok ? res : Promise.reject(res)))
    .then(res => res.json());

const Music = () => {
    const [ play, setPlay ] = useState({
        currentTrack: null,
        play: false
    });

    return (
        <ul className="music">
            <ReactHowler src={currentTrack} playing={play} />
            <Async promiseFn={loadTracks}>
                <Async.Loading>Loading...</Async.Loading>
                <Async.Fulfilled>
                    {data => {
                        return (
                            Object.keys(data[title].tracks).map(track => {console.log(data[title].tracks);
                                return(
                                <li key={data[title].tracks[track].filename}>
                                    <button 
                                        data-permalink={data[title].tracks[track].title}
                                        onClick={() => setPlay({currentTrack: data[title].tracks[track].filename, play: !play})}>
                                        {data[title].tracks[track].title}
                                    </button>
                                </li>
                            )})
                        )
                    }}
                </Async.Fulfilled>
                <Async.Rejected>
                    {error => `Something went wrong: ${error.message}`}
                </Async.Rejected>
            </Async>
        </ul>
    );
}

export default Music;

我还没有熟悉 React 功能组件,我了解基础知识,但我不知道如何将它与音频播放器之类的东西结合起来。

我对 Howler 并没有特别的兴趣,所以欢迎任何关于如何让它发挥作用的建议。

【问题讨论】:

    标签: reactjs html5-audio playlist howler.js


    【解决方案1】:

    我让它使用纯 HTML5 音频元素,不需要咆哮:

    import React, { useState, useEffect, useRef } from 'react';
    import Async from 'react-async';
    
    function countDown(duration, time) {
        if (!isNaN(time)) {
            var timeLeft = duration - time;
            return (
                Math.floor(timeLeft / 60) + ":" + ("0" + Math.floor(timeLeft % 60)).slice(-2)
            );
        }
    }
    
    const loadTracks = () =>
        fetch('...')
        .then(res => (res.ok ? res : Promise.reject(res)))
        .then(res => res.json());
    
    const Music = () => {
        const player = useRef(null);
        const [ state, setState ] = useState({
            currentTrack: null,
            currentTime: null,
            duration: null
        });
        let currentTime = getTime(state.currentTime);
        let duration = getTime(state.duration);
        let timeLeft = countDown(state.duration, state.currentTime);
        let currentTrack = null;
    
        useEffect(() => {
            if (state.currentTrack) {
                player.current.src = state.currentTrack;
                player.current.play();
            }
            player.current.addEventListener('timeupdate', e => {
                setState(prevState => ({
                    currentTime: e.target.currentTime,
                    duration: e.target.duration,
                    currentTrack: prevState.currentTrack
                }));
            });
    
            return function cleanup() {
                player.current.removeEventListener('timeupdate', () => {});
            }
        }, [state.currentTrack]);
    
        return (
            <ul className="music">
                <Async promiseFn={loadTracks}>
                    <Async.Loading>Loading...</Async.Loading>
                    <Async.Fulfilled>
                        {data => {
                            return (
                                Object.keys(data[title].tracks).map(track => {console.log(data[title].tracks);
                                    return(
                                    <li key={data[title].tracks[track].filename}>
                                        <button 
                                            data-permalink={data[title].tracks[track].title}
                                            onClick={() => setState({currentTrack: data[title].tracks[track].filename})}>
                                            {data[title].tracks[track].title}
                                        </button>
                                    </li>
                                )})
                            )
                        }}
                    </Async.Fulfilled>
                    <Async.Rejected>
                        {error => `Something went wrong: ${error.message}`}
                    </Async.Rejected>
                </Async>
            </ul>
        );
    }
    
    export default Music;
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-09-11
      • 2015-12-09
      • 1970-01-01
      • 2017-06-03
      • 1970-01-01
      相关资源
      最近更新 更多