个人Web音乐播放器实践

个人Web音乐播放器实践小结 React + Redux

  • web音乐播放器实践
    • 技术栈及相关组件
    • 遇到的问题及解决方法
      • redux 数据管理
      • 自定义滚动条组件 react-scrollbar
      • 首页歌单数据异步请求保证渲染顺序

web音乐播放器实践

在线预览传送门:http://iblossomspace.com/onlineMusicPlayer

本项目仅作学习交流使用,歌曲版权归QQ音乐所有!

技术栈及相关组件

相关技术栈:react.js + react-router-dom + redux
使用到的第三方 react 组件:swiper + react-scrollbar

遇到的问题及解决方法

redux 数据管理

使用 redux 管理当前正在播放的歌曲、播放列表、播放历史、收藏的歌曲数据。
在路由跳转的多个页面中都需要获取以上数据,为了避免将数据在组件树上自上而下层层传递,再自下而上层层传递的繁复操作,此处使用 redux 管理以上数据。

redux 具体使用方法在此不做赘述了。

自定义滚动条组件 react-scrollbar

自定义滚动条的 react 组件有很多,此处我选择了 react-scrollbar ,该组件满足滚动条的滚动、拖拽、点击需求。
在歌曲播放进度更新,需要同步移动歌词区域的滚动条时,需要使用该组件提供的 scrollYTo(topPosition) 方法。根据 npm 官网上该组件的文档描述,该方法挂载在组件实例的 context 属性的 scrollArea 对象下,由于 react.js 的更新使得 context 相关的API有明显差异,而该组件是基于旧版本的 context API 进行封装的,始终无法根据文档提示的方法获取。
虽然如此,但是通过 ref 获取组件实例后发现,组件实例下就存在 scrollArea 这个对象,自然也能使用 scrollArea 下面的那些API了。

 this._scrollArea=scrollArea}
>
this._scrollLyrics.scrollArea.scrollYTo(34 * (this.state.currentIndex - 4))

首页歌单数据异步请求保证渲染顺序

根据以下顺序请求接口并保证每次渲染顺序一致。在整个实践中,我使用了fetch 来请求数据。

// 首页推荐歌单
export const homeSheet = [
  { name: "流行音乐", id: 4 },
  { name: "热门歌曲", id: 26 },
  { name: "最新音乐", id: 27 },
  { name: "网络歌曲", id: 28 }
];

使用 Promise.all() 方法进行封装,结合 fetch ,请求到的数据依次请求完并按照顺序存入数组后,再使用 setState 更新视图数据。

// 获取分类歌单
getSheets = async () => {
  const resArr = await Promise.all((function () {
    const fetches = [];
    homeSheet.forEach(item => {
      fetches.push(fetch(api.topid + item.id))
    })
    return fetches;
  })());

  const dataArr = await Promise.all((function () {
    const datas = [];
    resArr.forEach(item => {
      datas.push(item.json());
    })
    return datas;
  })());

  const sheets = [];
  dataArr.forEach((item, index) => {
    sheets.push({
      id: homeSheet[index].id,
      name: homeSheet[index].name,
      songs: item.songs
    })
  })

  this.setState({ sheets })
}

不过,这样便降低了性能,每次载入首页都较为耗时。
同时,若在组件 setState 数据渲染完成前就切换到其它路由页面,则会报错(因为还有 setState 这个异步操作未完成,提示建议在 componentWillUnmount 这个钩子函数中取消操作)。
此处我为了解决报错提示,直接显示 Loading 组件遮罩在最上层,等待视图中的数据异步渲染完成后再隐藏 Loading 组件。但是因操作耗时 Loading 组件显示的时间略微有些长。

此处暂待优化。

文中所述若有不当之处,敬请批评指正,谢谢!

你可能感兴趣的:(实践小结)