正在显示
8 个修改的文件
包含
80 行增加
和
21 行删除
dist/McuClient.js
已删除
100644 → 0
此 diff 太大无法显示。
| @@ -421,14 +421,14 @@ export default class MessageEntrance extends Emiter { | @@ -421,14 +421,14 @@ export default class MessageEntrance extends Emiter { | ||
| 421 | GlobalConfig.MCUServerPort = _data.mcuList[0].port || ""; | 421 | GlobalConfig.MCUServerPort = _data.mcuList[0].port || ""; |
| 422 | } | 422 | } |
| 423 | 423 | ||
| 424 | - //视频推流播流地址 | 424 | + //上课中视频推流播流地址 |
| 425 | if (_data.msList&&_data.msList.length>0) { | 425 | if (_data.msList&&_data.msList.length>0) { |
| 426 | //MS地址默认使用第一个 | 426 | //MS地址默认使用第一个 |
| 427 | GlobalConfig.MSServerIP = _data.msList[0].ip || ""; | 427 | GlobalConfig.MSServerIP = _data.msList[0].ip || ""; |
| 428 | GlobalConfig.MSServerPort = _data.msList[0].port || ""; | 428 | GlobalConfig.MSServerPort = _data.msList[0].port || ""; |
| 429 | } | 429 | } |
| 430 | 430 | ||
| 431 | - //m3u8播流地址 | 431 | + //录制回放时m3u8播流地址 |
| 432 | if (_data.rsList&&_data.rsList.length>0) { | 432 | if (_data.rsList&&_data.rsList.length>0) { |
| 433 | //RS地址默认使用第一个 | 433 | //RS地址默认使用第一个 |
| 434 | GlobalConfig.RSServerIP = _data.rsList[0].ip || ""; | 434 | GlobalConfig.RSServerIP = _data.rsList[0].ip || ""; |
| @@ -323,7 +323,7 @@ GlobalConfig.mcuList=[];//录制服务器地址集合 | @@ -323,7 +323,7 @@ GlobalConfig.mcuList=[];//录制服务器地址集合 | ||
| 323 | GlobalConfig.msList=[];//ms服务器地址集合 | 323 | GlobalConfig.msList=[];//ms服务器地址集合 |
| 324 | GlobalConfig.musicList=[];//music服务器地址集合 | 324 | GlobalConfig.musicList=[];//music服务器地址集合 |
| 325 | GlobalConfig.musicListPrepare=[];//提提前上传的music集合 | 325 | GlobalConfig.musicListPrepare=[];//提提前上传的music集合 |
| 326 | -GlobalConfig.rsList=[]; | 326 | +GlobalConfig.rsList=[];//录制回放中视频点播地址 |
| 327 | 327 | ||
| 328 | 328 | ||
| 329 | GlobalConfig.country ="";//国家 | 329 | GlobalConfig.country ="";//国家 |
| @@ -32,6 +32,7 @@ class RecordPlayBackParse extends Emiter { | @@ -32,6 +32,7 @@ class RecordPlayBackParse extends Emiter { | ||
| 32 | console.log(parseBuffer); | 32 | console.log(parseBuffer); |
| 33 | this._recordPlaybackTimestamp = 0;//回放的时间 | 33 | this._recordPlaybackTimestamp = 0;//回放的时间 |
| 34 | this._recordPlaybackMaxTime = 0;//录制回放的总时间 | 34 | this._recordPlaybackMaxTime = 0;//录制回放的总时间 |
| 35 | + this._isReady=false;//录制回放是否已经准备完成 | ||
| 35 | this._apes = {}; | 36 | this._apes = {}; |
| 36 | this._messages = {}; | 37 | this._messages = {}; |
| 37 | this._timerCounter = new TimerCounter();//计时器 | 38 | this._timerCounter = new TimerCounter();//计时器 |
| @@ -109,7 +110,7 @@ class RecordPlayBackParse extends Emiter { | @@ -109,7 +110,7 @@ class RecordPlayBackParse extends Emiter { | ||
| 109 | this._recordPlaybackTimestamp = this._recordPlaybackTimestamp + 1;//计时 | 110 | this._recordPlaybackTimestamp = this._recordPlaybackTimestamp + 1;//计时 |
| 110 | if(this._recordPlaybackTimestamp>=this._recordPlaybackMaxTime){ | 111 | if(this._recordPlaybackTimestamp>=this._recordPlaybackMaxTime){ |
| 111 | this._stopTimerCounter(); | 112 | this._stopTimerCounter(); |
| 112 | - loger.log("录制结束...当前时间->", this._recordPlaybackTimestamp," 总时间->",this._recordPlaybackMaxTime); | 113 | + loger.log("录制回放结束...当前时间->", this._recordPlaybackTimestamp," 总时间->",this._recordPlaybackMaxTime); |
| 113 | this._emit(MessageTypes.RECORD_PLAYBACK_UPDATE,{"status":STOP}); | 114 | this._emit(MessageTypes.RECORD_PLAYBACK_UPDATE,{"status":STOP}); |
| 114 | return; | 115 | return; |
| 115 | } | 116 | } |
| @@ -123,6 +124,7 @@ class RecordPlayBackParse extends Emiter { | @@ -123,6 +124,7 @@ class RecordPlayBackParse extends Emiter { | ||
| 123 | 124 | ||
| 124 | //加载录制文件 | 125 | //加载录制文件 |
| 125 | readyRecordPlay() { | 126 | readyRecordPlay() { |
| 127 | + this._isReady=false; | ||
| 126 | this._stopTimerCounter(); | 128 | this._stopTimerCounter(); |
| 127 | loger.log("读取回放数据"); | 129 | loger.log("读取回放数据"); |
| 128 | //let url = `http://123.56.73.119:80/h5dev/20170306/1357644520_20170306.rec`; | 130 | //let url = `http://123.56.73.119:80/h5dev/20170306/1357644520_20170306.rec`; |
| @@ -191,6 +193,7 @@ class RecordPlayBackParse extends Emiter { | @@ -191,6 +193,7 @@ class RecordPlayBackParse extends Emiter { | ||
| 191 | this._recordPlaybackMaxTime=timestamp; | 193 | this._recordPlaybackMaxTime=timestamp; |
| 192 | } | 194 | } |
| 193 | this._recordPlaybackTimestamp=0; | 195 | this._recordPlaybackTimestamp=0; |
| 196 | + this._isReady=true; | ||
| 194 | this._stopTimerCounter(); | 197 | this._stopTimerCounter(); |
| 195 | 198 | ||
| 196 | GlobalConfig.recordPlaybackMaxTime=this._recordPlaybackMaxTime; | 199 | GlobalConfig.recordPlaybackMaxTime=this._recordPlaybackMaxTime; |
| @@ -204,7 +207,6 @@ class RecordPlayBackParse extends Emiter { | @@ -204,7 +207,6 @@ class RecordPlayBackParse extends Emiter { | ||
| 204 | let msgDataArr=this._messages[_timestamp]; | 207 | let msgDataArr=this._messages[_timestamp]; |
| 205 | if(!msgDataArr){ | 208 | if(!msgDataArr){ |
| 206 | //没有数据,需要查找当前时间点属于哪一个时间戳关键帧 | 209 | //没有数据,需要查找当前时间点属于哪一个时间戳关键帧 |
| 207 | - | ||
| 208 | }else { | 210 | }else { |
| 209 | //把时间点对应的数据发送,同一秒内有存在多个数据的情况 | 211 | //把时间点对应的数据发送,同一秒内有存在多个数据的情况 |
| 210 | for(let i=0;i<msgDataArr.length;i++){ | 212 | for(let i=0;i<msgDataArr.length;i++){ |
| @@ -214,31 +216,68 @@ class RecordPlayBackParse extends Emiter { | @@ -214,31 +216,68 @@ class RecordPlayBackParse extends Emiter { | ||
| 214 | } | 216 | } |
| 215 | //method------------外部接口------------------------------------- | 217 | //method------------外部接口------------------------------------- |
| 216 | 218 | ||
| 219 | + //开始播放 | ||
| 217 | startRecordPlayback(_param) { | 220 | startRecordPlayback(_param) { |
| 221 | + if(!this._isReady){ | ||
| 222 | + return {"code": ApeConsts.RETURN_FAILED,"data": "录制回放还未准备完成"}; | ||
| 223 | + } | ||
| 218 | this._startTimerCounter(); | 224 | this._startTimerCounter(); |
| 219 | - return {"code": ApeConsts.RETURN_SUCCESS,"data": "ok"}; | ||
| 220 | - //this._apes(MessageTypes.RECORD_PLAYBACK_UPDATE,{"status":}); | 225 | + this._emit(MessageTypes.RECORD_PLAYBACK_UPDATE,{"status":PLAY}); |
| 221 | } | 226 | } |
| 222 | 227 | ||
| 228 | + //停止播放 | ||
| 223 | stopRecordPlayback(_param) { | 229 | stopRecordPlayback(_param) { |
| 224 | this._recordPlaybackTimestamp = 0; | 230 | this._recordPlaybackTimestamp = 0; |
| 225 | this._stopTimerCounter(); | 231 | this._stopTimerCounter(); |
| 226 | - return {"code": ApeConsts.RETURN_SUCCESS,"data": "ok"}; | 232 | + this._emit(MessageTypes.RECORD_PLAYBACK_UPDATE,{"status":STOP}); |
| 227 | } | 233 | } |
| 228 | 234 | ||
| 235 | + //暂停播放 | ||
| 229 | pauseRecordPlayback(_param) { | 236 | pauseRecordPlayback(_param) { |
| 230 | - this._stopTimerCounter() | ||
| 231 | - return {"code": ApeConsts.RETURN_SUCCESS,"data": "ok"}; | 237 | + this._stopTimerCounter(); |
| 238 | + this._emit(MessageTypes.RECORD_PLAYBACK_UPDATE,{"status":PAUSE}); | ||
| 232 | } | 239 | } |
| 233 | 240 | ||
| 241 | + //跳转到指定时间点播放 | ||
| 234 | seekRecordPlayback(_param) { | 242 | seekRecordPlayback(_param) { |
| 243 | + if(!this._isReady){ | ||
| 244 | + return {"code": ApeConsts.RETURN_FAILED,"data": "录制回放还未准备完成"}; | ||
| 245 | + } | ||
| 235 | if(!_param||!_param.time){ | 246 | if(!_param||!_param.time){ |
| 236 | return {"code": ApeConsts.RETURN_FAILED,"data": "参数不正确"}; | 247 | return {"code": ApeConsts.RETURN_FAILED,"data": "参数不正确"}; |
| 237 | } | 248 | } |
| 249 | + //先暂停,更改进行的时间 | ||
| 238 | this._stopTimerCounter() | 250 | this._stopTimerCounter() |
| 239 | this._recordPlaybackTimestamp = _param.time || 0; | 251 | this._recordPlaybackTimestamp = _param.time || 0; |
| 252 | + | ||
| 253 | + //查找关键帧 | ||
| 254 | + this._searchKeyFram(); | ||
| 255 | + } | ||
| 256 | + _searchKeyFram(){ | ||
| 257 | + //查找关键帧,找到关键帧后再继续播放 | ||
| 258 | + let messageItem; | ||
| 259 | + let keyFrameSeek=0; | ||
| 260 | + for(let i=this._recordPlaybackTimestamp;i>0;i--){ | ||
| 261 | + messageItem=this._messages[i]; | ||
| 262 | + if(messageItem){ | ||
| 263 | + break; | ||
| 264 | + } | ||
| 265 | + } | ||
| 266 | + if(messageItem){ | ||
| 267 | + keyFrameSeek=(this._recordPlaybackTimestamp-messageItem.timestamp) | ||
| 268 | + loger.log("SEEK->",this._recordPlaybackTimestamp,"查找到相连的数据,seek和关键帧的位置偏移",keyFrameSeek,"秒"); | ||
| 269 | + //把时间点对应的数据发送,同一秒内有存在多个数据的情况 | ||
| 270 | + for(let i=0;i<messageItem.length;i++){ | ||
| 271 | + this._everSocketMsgReceivedHandler(messageItem[i].byteData); | ||
| 272 | + } | ||
| 273 | + }else { | ||
| 274 | + loger.log("SEEK->",this._recordPlaybackTimestamp,"没有查找到相连的数据"); | ||
| 275 | + } | ||
| 276 | + | ||
| 277 | + this._emit(MessageTypes.RECORD_PLAYBACK_UPDATE,{"status":SEEK,"keyFrameSeek":keyFrameSeek}); | ||
| 278 | + //无论有没有找到关键帧数据,都继续播放 | ||
| 240 | this._startTimerCounter(); | 279 | this._startTimerCounter(); |
| 241 | - return {"code": ApeConsts.RETURN_SUCCESS,"data": "ok"}; | 280 | + |
| 242 | } | 281 | } |
| 243 | } | 282 | } |
| 244 | 283 |
| @@ -51,14 +51,6 @@ export default class Ape extends Emiter { | @@ -51,14 +51,6 @@ export default class Ape extends Emiter { | ||
| 51 | 51 | ||
| 52 | //先收到onJoinSessionHandlerSuccess 后收到 onJoinChannelHandlerSuccess | 52 | //先收到onJoinSessionHandlerSuccess 后收到 onJoinChannelHandlerSuccess |
| 53 | 53 | ||
| 54 | - loger.log('APE-->registerApe->', | ||
| 55 | - 'SessionId', | ||
| 56 | - this._session_id, | ||
| 57 | - 'SessionName', | ||
| 58 | - this._session_name, | ||
| 59 | - 'SessionTag', | ||
| 60 | - this._session_tag); | ||
| 61 | - | ||
| 62 | // 监听底层MCU课堂 | 54 | // 监听底层MCU课堂 |
| 63 | this.mcu = McuObj; | 55 | this.mcu = McuObj; |
| 64 | this.mcu.on(MessageTypes.CLASS_JOIN_MCU_SUCCESS, this._mcuConferenceJoinSuccessHandler.bind(this)); | 56 | this.mcu.on(MessageTypes.CLASS_JOIN_MCU_SUCCESS, this._mcuConferenceJoinSuccessHandler.bind(this)); |
| @@ -316,14 +316,17 @@ class AudioApe extends Ape { | @@ -316,14 +316,17 @@ class AudioApe extends Ape { | ||
| 316 | if(unpackChannelInfo&&unpackChannelInfo.fromNodeId!=GlobalConfig.nodeId){ | 316 | if(unpackChannelInfo&&unpackChannelInfo.fromNodeId!=GlobalConfig.nodeId){ |
| 317 | let receiveChannelInfo={}; | 317 | let receiveChannelInfo={}; |
| 318 | receiveChannelInfo.mediaId=unpackChannelInfo.channelId; | 318 | receiveChannelInfo.mediaId=unpackChannelInfo.channelId; |
| 319 | + receiveChannelInfo.fromNodeId=unpackChannelInfo.fromNodeId; | ||
| 319 | 320 | ||
| 320 | //消息不是自己同步的,需要处理 | 321 | //消息不是自己同步的,需要处理 |
| 321 | if(unpackChannelInfo.status==ApeConsts.CHANNEL_STATUS_OPENING){ | 322 | if(unpackChannelInfo.status==ApeConsts.CHANNEL_STATUS_OPENING){ |
| 322 | //正在推流 | 323 | //正在推流 |
| 323 | receiveChannelInfo.m3u8Url=""; | 324 | receiveChannelInfo.m3u8Url=""; |
| 324 | receiveChannelInfo.rtmpUrl=""; | 325 | receiveChannelInfo.rtmpUrl=""; |
| 326 | + receiveChannelInfo.replay=""; | ||
| 325 | let m3u8Stream=this.mediaModule.getMediaPlayPath({"type":"m3u8","streamId": unpackChannelInfo.streamId}); | 327 | let m3u8Stream=this.mediaModule.getMediaPlayPath({"type":"m3u8","streamId": unpackChannelInfo.streamId}); |
| 326 | let rtmpStream=this.mediaModule.getMediaPlayPath({"type":"rtmp","streamId": unpackChannelInfo.streamId}); | 328 | let rtmpStream=this.mediaModule.getMediaPlayPath({"type":"rtmp","streamId": unpackChannelInfo.streamId}); |
| 329 | + let replay=this.mediaModule.getMediaRecordPlaybackPath({"type":"m3u8","streamId": unpackChannelInfo.streamId}); | ||
| 327 | 330 | ||
| 328 | if(m3u8Stream.code==0){ | 331 | if(m3u8Stream.code==0){ |
| 329 | receiveChannelInfo.m3u8Url=m3u8Stream.playUrl; | 332 | receiveChannelInfo.m3u8Url=m3u8Stream.playUrl; |
| @@ -331,6 +334,9 @@ class AudioApe extends Ape { | @@ -331,6 +334,9 @@ class AudioApe extends Ape { | ||
| 331 | if(rtmpStream.code==0){ | 334 | if(rtmpStream.code==0){ |
| 332 | receiveChannelInfo.rtmpUrl=rtmpStream.playUrl; | 335 | receiveChannelInfo.rtmpUrl=rtmpStream.playUrl; |
| 333 | } | 336 | } |
| 337 | + if(replay.code==0){ | ||
| 338 | + receiveChannelInfo.replay=replay.playUrl; | ||
| 339 | + } | ||
| 334 | loger.log("AUDIO_PLAY",receiveChannelInfo); | 340 | loger.log("AUDIO_PLAY",receiveChannelInfo); |
| 335 | //广播播放视频的消息 | 341 | //广播播放视频的消息 |
| 336 | this._emit(MessageTypes.AUDIO_PLAY, receiveChannelInfo); | 342 | this._emit(MessageTypes.AUDIO_PLAY, receiveChannelInfo); |
| @@ -32,7 +32,7 @@ class MediaModule { | @@ -32,7 +32,7 @@ class MediaModule { | ||
| 32 | let port=""; | 32 | let port=""; |
| 33 | if (_param.type == "m3u8") { | 33 | if (_param.type == "m3u8") { |
| 34 | //M3U8 | 34 | //M3U8 |
| 35 | - //http://123.56.73.119:6001/hls/h5dev_403074980_0_983041_1487663265/index.m3u8 | 35 | + //http://123.56.73.119:6001/live/h5dev_2106728010_8ab3b0ed5a3a9220015a3a958f0d0003_983041_1489113860/index.m3u8 |
| 36 | port = (GlobalConfig.RSServerPort == "" || GlobalConfig.RSServerPort == null) ? "":":" + GlobalConfig.RSServerPort; | 36 | port = (GlobalConfig.RSServerPort == "" || GlobalConfig.RSServerPort == null) ? "":":" + GlobalConfig.RSServerPort; |
| 37 | path = "http://" + GlobalConfig.RSServerIP | 37 | path = "http://" + GlobalConfig.RSServerIP |
| 38 | + port + "/live/" | 38 | + port + "/live/" |
| @@ -47,6 +47,23 @@ class MediaModule { | @@ -47,6 +47,23 @@ class MediaModule { | ||
| 47 | return {"code": ApeConsts.RETURN_SUCCESS, "data": "","playUrl": path}; | 47 | return {"code": ApeConsts.RETURN_SUCCESS, "data": "","playUrl": path}; |
| 48 | } | 48 | } |
| 49 | 49 | ||
| 50 | + //获取录制回放时点播的地址,只有m3u8 | ||
| 51 | + getMediaRecordPlaybackPath(_param) { | ||
| 52 | + loger.log('getMediaRecordPlaybackPath'); | ||
| 53 | + if (_param == null||_param.streamId == null) | ||
| 54 | + { | ||
| 55 | + loger.warn('getMediaRecordPlaybackPath,参数错误', _param); | ||
| 56 | + return {"code": ApeConsts.RETURN_FAILED, "data": ""}; | ||
| 57 | + } | ||
| 58 | + //M3U8 http://123.56.73.119:6001/live/h5dev_2106728010_8ab3b0ed5a3a9220015a3a958f0d0003_983041_1489113860/total.m3u8 | ||
| 59 | + let port = (GlobalConfig.RSServerPort == "" || GlobalConfig.RSServerPort == null) ? "":":" + GlobalConfig.RSServerPort; | ||
| 60 | + let path = "http://" + GlobalConfig.RSServerIP | ||
| 61 | + + port + "/live/" | ||
| 62 | + + _param.streamId | ||
| 63 | + + "/total.m3u8"; | ||
| 64 | + return {"code": ApeConsts.RETURN_SUCCESS, "data": "","playUrl": path}; | ||
| 65 | + } | ||
| 66 | + | ||
| 50 | //获取推流地址 | 67 | //获取推流地址 |
| 51 | getMediaPublishPath(_param) { | 68 | getMediaPublishPath(_param) { |
| 52 | loger.log('getMediaPublishPath'); | 69 | loger.log('getMediaPublishPath'); |
| @@ -319,14 +319,16 @@ class VideoApe extends Ape { | @@ -319,14 +319,16 @@ class VideoApe extends Ape { | ||
| 319 | if(unpackChannelInfo&&unpackChannelInfo.fromNodeId!=GlobalConfig.nodeId){ | 319 | if(unpackChannelInfo&&unpackChannelInfo.fromNodeId!=GlobalConfig.nodeId){ |
| 320 | let receiveChannelInfo={}; | 320 | let receiveChannelInfo={}; |
| 321 | receiveChannelInfo.mediaId=unpackChannelInfo.channelId; | 321 | receiveChannelInfo.mediaId=unpackChannelInfo.channelId; |
| 322 | - | 322 | + receiveChannelInfo.fromNodeId=unpackChannelInfo.fromNodeId; |
| 323 | //消息不是自己同步的,需要处理 | 323 | //消息不是自己同步的,需要处理 |
| 324 | if(unpackChannelInfo.status==ApeConsts.CHANNEL_STATUS_OPENING){ | 324 | if(unpackChannelInfo.status==ApeConsts.CHANNEL_STATUS_OPENING){ |
| 325 | //正在推流 | 325 | //正在推流 |
| 326 | receiveChannelInfo.m3u8Url=""; | 326 | receiveChannelInfo.m3u8Url=""; |
| 327 | receiveChannelInfo.rtmpUrl=""; | 327 | receiveChannelInfo.rtmpUrl=""; |
| 328 | + receiveChannelInfo.replay=""; | ||
| 328 | let m3u8Stream=this.mediaModule.getMediaPlayPath({"type":"m3u8","streamId": unpackChannelInfo.streamId}); | 329 | let m3u8Stream=this.mediaModule.getMediaPlayPath({"type":"m3u8","streamId": unpackChannelInfo.streamId}); |
| 329 | let rtmpStream=this.mediaModule.getMediaPlayPath({"type":"rtmp","streamId": unpackChannelInfo.streamId}); | 330 | let rtmpStream=this.mediaModule.getMediaPlayPath({"type":"rtmp","streamId": unpackChannelInfo.streamId}); |
| 331 | + let replay=this.mediaModule.getMediaRecordPlaybackPath({"type":"m3u8","streamId": unpackChannelInfo.streamId}); | ||
| 330 | 332 | ||
| 331 | if(m3u8Stream.code==0){ | 333 | if(m3u8Stream.code==0){ |
| 332 | receiveChannelInfo.m3u8Url=m3u8Stream.playUrl; | 334 | receiveChannelInfo.m3u8Url=m3u8Stream.playUrl; |
| @@ -334,6 +336,9 @@ class VideoApe extends Ape { | @@ -334,6 +336,9 @@ class VideoApe extends Ape { | ||
| 334 | if(rtmpStream.code==0){ | 336 | if(rtmpStream.code==0){ |
| 335 | receiveChannelInfo.rtmpUrl=rtmpStream.playUrl; | 337 | receiveChannelInfo.rtmpUrl=rtmpStream.playUrl; |
| 336 | } | 338 | } |
| 339 | + if(replay.code==0){ | ||
| 340 | + receiveChannelInfo.replay=replay.playUrl; | ||
| 341 | + } | ||
| 337 | loger.log("VIDEO_PLAY",receiveChannelInfo); | 342 | loger.log("VIDEO_PLAY",receiveChannelInfo); |
| 338 | //广播播放视频的消息 | 343 | //广播播放视频的消息 |
| 339 | this._emit(MessageTypes.VIDEO_PLAY, receiveChannelInfo); | 344 | this._emit(MessageTypes.VIDEO_PLAY, receiveChannelInfo); |
-
请 注册 或 登录 后发表评论