• React使用西瓜播放器


    西瓜播放器 | 快速上手

    概述

    西瓜播放器是一个Web视频播放器类库,它本着一切都是组件化的原则设计了独立可拆卸的 UI 组件。更重要的是它不只是在 UI 层有灵活的表现,在功能上也做了大胆的尝试:摆脱视频加载、缓冲、格式支持对 video 的依赖。尤其是在 mp4 点播上做了较大的努力,让本不支持流式播放的 mp4 能做到分段加载,这就意味着可以做到清晰度无缝切换、加载控制、节省视频流量。同时,它也集成了对 flv、hls、dash 的点播和直播支持。

    安装:

    1. npm install xgplayer
    2. npm install xgplayer-flv
    3. npm install xgplayer-hls

    按需引入即可,代码如下:

    1. import MonitorLiveBroadComp from "./pages/Monitor/index";
    2. import { useEffect, useState } from 'react'
    3. import logo from './logo.svg'
    4. import './App.css';
    5. import mp4Player from 'xgplayer';
    6. import flvPlayer from 'xgplayer-flv';
    7. import hlsPlayer from 'xgplayer-hls';
    8. import ismobilejs from 'ismobilejs';
    9. import picNotStart from './assets/img/img_video_default_notstart@2x.png';
    10. import picTranscode from './assets/img/img_video_default_transcoding@2x.png';
    11. import querystring from 'query-string';
    12. import { apiHost } from "./hosts";
    13. const {cid, token} = querystring.parse(window.location.search);
    14. if (!cid || !token) console.warn('需要token和cid信息');
    15. const isMobile = ismobilejs();
    16. enum clsSt {
    17. wait = 0,
    18. earlyExtra = 3,
    19. during = 1,
    20. lateExtra = 4,
    21. end = 2,
    22. }
    23. function App() {
    24. const [mode, setMode] = useState<'hls'|'flv'|'mp4'|'stop'|'wait'|'transcode'>('wait');
    25. const [url, setUrl] = useState('');
    26. useEffect(() => {
    27. fetch(apiHost+`/api/client/monitor/stream?classroomId=${cid}`, {
    28. method: 'GET',
    29. headers: { token: ''+token }
    30. }).then(data => data.json()).then(json => {
    31. if (json.code !== 200) throw new Error(`获取推流信息失败(${json.code}, ${json.msg}).`);
    32. const {status, streamUrl, videoUrl} = json.data;
    33. const inClass = [clsSt.earlyExtra, clsSt.lateExtra, clsSt.during].indexOf(status) > -1;
    34. if (inClass && streamUrl) {
    35. const streamType = isMobile.apple.device ? 'hls' : 'flv';
    36. setMode(streamType);
    37. setUrl(streamUrl.replace(/\.(flv|m3u8)$/, streamType === 'flv' ? '.flv' : '.m3u8'));
    38. } else if (inClass) {
    39. setMode('stop');
    40. setUrl('');
    41. } else if (status === clsSt.end && videoUrl) {
    42. setMode('mp4');
    43. setUrl(videoUrl);
    44. } else if (status === clsSt.end && !videoUrl) {
    45. setMode('transcode');
    46. setUrl('');
    47. }
    48. }).catch(err => {console.error(err)});
    49. return () => {}
    50. }, []);
    51. useEffect(() => {
    52. const Player = ({
    53. 'flv': flvPlayer,
    54. 'hls': hlsPlayer,
    55. 'mp4': mp4Player,
    56. } as any)[mode];
    57. let playerIns: any;
    58. url && setTimeout(() => {
    59. playerIns = new Player(Object.assign({
    60. id: 'monitorVideo',
    61. url: url,
    62. width: '100%',
    63. height: '100%',
    64. playsinline: true,
    65. closeVideoTouch: true,
    66. ignores: ['fullscreen'],
    67. }, ({
    68. 'flv': {
    69. isLive: true,
    70. preloadTime: 30,
    71. minCachedTime: 5,
    72. // cors: false,
    73. },
    74. 'hls': {
    75. isLive: true,
    76. config: {duration: NaN}
    77. },
    78. 'mp4' : {
    79. playbackRate: [0.5, 0.75, 1, 1.5, 2],
    80. },
    81. }as any)[mode]));
    82. mode === 'hls' && Object.defineProperty(playerIns, 'duration', {value: NaN});
    83. }, 0)
    84. return () => {
    85. playerIns?.pause();
    86. playerIns?.destroy();
    87. };
    88. }, [url, mode]);
    89. return (
    90. <div className={isMobile.apple.tablet ? 'App ipad' : 'App'}>
    91. <div className="video-wrap">
    92. <div id="monitorVideo" className="video-container">div>
    93. {mode === 'transcode' && <div className="notify"><img src={picNotStart} alt="" /><p>视频转码中...p>div> }
    94. {mode === 'wait' && <div className="notify"><img src={picTranscode} alt="" /><p>课程尚未开始p>div> }
    95. {mode === 'stop' && <div className="notify"><p>主讲可能退出教室,请尝试刷新p>div> }
    96. div>
    97. <MonitorLiveBroadComp />
    98. div>
    99. )
    100. }
    101. export default App

  • 相关阅读:
    MATLAB嵌套if语句
    热门Java开发工具IDEA入门指南——IDEA默认用户界面
    雷电模拟器谷歌套件安装的时候总是卡着转圈圈
    恶意加密流量检测
    数据结构之跳表
    浅尝KBQA中使用语义角色标注进行约束挂载
    强制类型转换有哪几种?
    并查集——最小生成树算法Kruskal
    【测控电路】微积分电路
    2013年12月1日 Go生态洞察:Go 1.2版本发布
  • 原文地址:https://blog.csdn.net/weixin_42333548/article/details/126857226