1 line
11 KiB
JavaScript
1 line
11 KiB
JavaScript
define(["exports","../utils/events.js","../utils/logger.js","../../browser.js","./mse-events.js","./media-segment-info.js","../utils/exception.js"],function(_exports,_events,_logger,_browser,_mseEvents,_mediaSegmentInfo,_exception){Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.default=void 0;var MSEController=function(){function MSEController(config){babelHelpers.classCallCheck(this,MSEController),this.TAG="MSEController",this._config=config,this._emitter=new _events.default,this._config.isLive&&!this._config.autoCleanupSourceBuffer&&(this._config.autoCleanupSourceBuffer=!0),this.e={onSourceOpen:this._onSourceOpen.bind(this),onSourceEnded:this._onSourceEnded.bind(this),onSourceClose:this._onSourceClose.bind(this),onSourceBufferError:this._onSourceBufferError.bind(this),onSourceBufferUpdateEnd:this._onSourceBufferUpdateEnd.bind(this)},this._mediaSource=null,this._mediaSourceObjectURL=null,this._mediaElement=null,this._isBufferFull=!1,this._hasPendingEos=!1,this._requireSetMediaDuration=!1,this._pendingMediaDuration=0,this._pendingSourceBufferInit=[],this._mimeTypes={video:null,audio:null},this._sourceBuffers={video:null,audio:null},this._lastInitSegments={video:null,audio:null},this._pendingSegments={video:[],audio:[]},this._pendingRemoveRanges={video:[],audio:[]},this._idrList=new _mediaSegmentInfo.IDRSampleList}return babelHelpers.createClass(MSEController,[{key:"destroy",value:function(){(this._mediaElement||this._mediaSource)&&this.detachMediaElement(),this.e=null,this._emitter.removeAllListeners(),this._emitter=null}},{key:"on",value:function(event,listener){this._emitter.addListener(event,listener)}},{key:"off",value:function(event,listener){this._emitter.removeListener(event,listener)}},{key:"attachMediaElement",value:function(mediaElement){if(this._mediaSource)throw new _exception.IllegalStateException("MediaSource has been attached to an HTMLMediaElement!");var ms=this._mediaSource=new window.MediaSource;ms.addEventListener("sourceopen",this.e.onSourceOpen),ms.addEventListener("sourceended",this.e.onSourceEnded),ms.addEventListener("sourceclose",this.e.onSourceClose),this._mediaElement=mediaElement,this._mediaSourceObjectURL=window.URL.createObjectURL(this._mediaSource),mediaElement.src=this._mediaSourceObjectURL}},{key:"detachMediaElement",value:function(){if(this._mediaSource){var type,ms=this._mediaSource;for(type in this._sourceBuffers){var ps=this._pendingSegments[type],ps=(ps.splice(0,ps.length),this._pendingSegments[type]=null,this._pendingRemoveRanges[type]=null,this._lastInitSegments[type]=null,this._sourceBuffers[type]);if(ps){if("closed"!==ms.readyState){try{ms.removeSourceBuffer(ps)}catch(error){_logger.default.e(this.TAG,error.message)}ps.removeEventListener("error",this.e.onSourceBufferError),ps.removeEventListener("updateend",this.e.onSourceBufferUpdateEnd)}this._mimeTypes[type]=null,this._sourceBuffers[type]=null}}if("open"===ms.readyState)try{ms.endOfStream()}catch(error){_logger.default.e(this.TAG,error.message)}ms.removeEventListener("sourceopen",this.e.onSourceOpen),ms.removeEventListener("sourceended",this.e.onSourceEnded),ms.removeEventListener("sourceclose",this.e.onSourceClose),this._pendingSourceBufferInit=[],this._isBufferFull=!1,this._idrList.clear(),this._mediaSource=null}this._mediaElement&&(this._mediaElement.src="",this._mediaElement.removeAttribute("src"),this._mediaElement=null),this._mediaSourceObjectURL&&(window.URL.revokeObjectURL(this._mediaSourceObjectURL),this._mediaSourceObjectURL=null)}},{key:"appendInitSegment",value:function(initSegment,deferred){if(this._mediaSource&&"open"===this._mediaSource.readyState){var is=initSegment,mimeType="".concat(is.container),firstInitSegment=(is.codec&&0<is.codec.length&&(mimeType+=";codecs=".concat(is.codec)),!1);if(_logger.default.v(this.TAG,"Received Initialization Segment, mimeType: "+mimeType),this._lastInitSegments[is.type]=is,mimeType!==this._mimeTypes[is.type]){if(this._mimeTypes[is.type])_logger.default.v(this.TAG,"Notice: ".concat(is.type," mimeType changed, origin: ").concat(this._mimeTypes[is.type],", target: ").concat(mimeType));else{firstInitSegment=!0;try{var sb=this._sourceBuffers[is.type]=this._mediaSource.addSourceBuffer(mimeType);sb.addEventListener("error",this.e.onSourceBufferError),sb.addEventListener("updateend",this.e.onSourceBufferUpdateEnd)}catch(error){return _logger.default.e(this.TAG,error.message),void this._emitter.emit(_mseEvents.default.ERROR,{code:error.code,msg:error.message})}}this._mimeTypes[is.type]=mimeType}deferred||this._pendingSegments[is.type].push(is),firstInitSegment||this._sourceBuffers[is.type]&&!this._sourceBuffers[is.type].updating&&this._doAppendSegments(),_browser.default.safari&&"audio/mpeg"===is.container&&0<is.mediaDuration&&(this._requireSetMediaDuration=!0,this._pendingMediaDuration=is.mediaDuration/1e3,this._updateMediaSourceDuration())}else this._pendingSourceBufferInit.push(initSegment),this._pendingSegments[initSegment.type].push(initSegment)}},{key:"appendMediaSegment",value:function(mediaSegment){this._pendingSegments[mediaSegment.type].push(mediaSegment),this._config.autoCleanupSourceBuffer&&this._needCleanupSourceBuffer()&&this._doCleanupSourceBuffer(),mediaSegment=this._sourceBuffers[mediaSegment.type];!mediaSegment||mediaSegment.updating||this._hasPendingRemoveRanges()||this._doAppendSegments()}},{key:"seek",value:function(seconds){for(var type in this._sourceBuffers)if(this._sourceBuffers[type]){var sb=this._sourceBuffers[type];if("open"===this._mediaSource.readyState)try{sb.abort()}catch(error){_logger.default.e(this.TAG,error.message)}this._idrList.clear();var ps=this._pendingSegments[type];if(ps.splice(0,ps.length),"closed"!==this._mediaSource.readyState){for(var i=0;i<sb.buffered.length;i++){var start=sb.buffered.start(i),end=sb.buffered.end(i);this._pendingRemoveRanges[type].push({start:start,end:end})}sb.updating||this._doRemoveRanges(),_browser.default.safari&&(ps=this._lastInitSegments[type])&&(this._pendingSegments[type].push(ps),sb.updating||this._doAppendSegments())}}}},{key:"endOfStream",value:function(){var ms=this._mediaSource,sb=this._sourceBuffers;ms&&"open"===ms.readyState?sb.video&&sb.video.updating||sb.audio&&sb.audio.updating?this._hasPendingEos=!0:(this._hasPendingEos=!1,ms.endOfStream()):ms&&"closed"===ms.readyState&&this._hasPendingSegments()&&(this._hasPendingEos=!0)}},{key:"getNearestKeyframe",value:function(dts){return this._idrList.getLastSyncPointBeforeDts(dts)}},{key:"_needCleanupSourceBuffer",value:function(){if(this._config.autoCleanupSourceBuffer){var type,currentTime=this._mediaElement.currentTime;for(type in this._sourceBuffers){var sb=this._sourceBuffers[type];if(sb){sb=sb.buffered;if(1<=sb.length&¤tTime-sb.start(0)>=this._config.autoCleanupMaxBackwardDuration)return!0}}}return!1}},{key:"_doCleanupSourceBuffer",value:function(){var type,currentTime=this._mediaElement.currentTime;for(type in this._sourceBuffers){var sb=this._sourceBuffers[type];if(sb){for(var buffered=sb.buffered,doRemove=!1,i=0;i<buffered.length;i++){var removeEnd,start=buffered.start(i),end=buffered.end(i);start<=currentTime&¤tTime<end+3?currentTime-start>=this._config.autoCleanupMaxBackwardDuration&&(doRemove=!0,removeEnd=currentTime-this._config.autoCleanupMinBackwardDuration,this._pendingRemoveRanges[type].push({start:start,end:removeEnd})):end<currentTime&&(doRemove=!0,this._pendingRemoveRanges[type].push({start:start,end:end}))}doRemove&&!sb.updating&&this._doRemoveRanges()}}}},{key:"_updateMediaSourceDuration",value:function(){var target,sb=this._sourceBuffers;0===this._mediaElement.readyState||"open"!==this._mediaSource.readyState||sb.video&&sb.video.updating||sb.audio&&sb.audio.updating||(sb=this._mediaSource.duration,0<(target=this._pendingMediaDuration)&&(isNaN(sb)||sb<target)&&(_logger.default.v(this.TAG,"Update MediaSource duration from ".concat(sb," to ").concat(target)),this._mediaSource.duration=target),this._requireSetMediaDuration=!1,this._pendingMediaDuration=0)}},{key:"_doRemoveRanges",value:function(){for(var type in this._pendingRemoveRanges)if(this._sourceBuffers[type]&&!this._sourceBuffers[type].updating)for(var sb=this._sourceBuffers[type],ranges=this._pendingRemoveRanges[type];ranges.length&&!sb.updating;){var range=ranges.shift();sb.remove(range.start,range.end)}}},{key:"_doAppendSegments",value:function(){var type,pendingSegments=this._pendingSegments;for(type in pendingSegments)if(this._sourceBuffers[type]&&!this._sourceBuffers[type].updating&&0<pendingSegments[type].length){var currentOffset,targetOffset,segment=pendingSegments[type].shift();if(segment.timestampOffset&&(currentOffset=this._sourceBuffers[type].timestampOffset,targetOffset=segment.timestampOffset/1e3,.1<Math.abs(currentOffset-targetOffset)&&(_logger.default.v(this.TAG,"Update MPEG audio timestampOffset from ".concat(currentOffset," to ").concat(targetOffset)),this._sourceBuffers[type].timestampOffset=targetOffset),delete segment.timestampOffset),segment.data&&0!==segment.data.byteLength)try{this._sourceBuffers[type].appendBuffer(segment.data),this._isBufferFull=!1,"video"===type&&Object.hasOwn(segment,"info")&&this._idrList.appendArray(segment.info.syncPoints)}catch(error){this._pendingSegments[type].unshift(segment),22===error.code?(this._isBufferFull||this._emitter.emit(_mseEvents.default.BUFFER_FULL),this._isBufferFull=!0):(_logger.default.e(this.TAG,error.message),this._emitter.emit(_mseEvents.default.ERROR,{code:error.code,msg:error.message}))}}}},{key:"_onSourceOpen",value:function(){if(_logger.default.v(this.TAG,"MediaSource onSourceOpen"),this._mediaSource.removeEventListener("sourceopen",this.e.onSourceOpen),0<this._pendingSourceBufferInit.length)for(var pendings=this._pendingSourceBufferInit;pendings.length;){var segment=pendings.shift();this.appendInitSegment(segment,!0)}this._hasPendingSegments()&&this._doAppendSegments(),this._emitter.emit(_mseEvents.default.SOURCE_OPEN)}},{key:"_onSourceEnded",value:function(){_logger.default.v(this.TAG,"MediaSource onSourceEnded")}},{key:"_onSourceClose",value:function(){_logger.default.v(this.TAG,"MediaSource onSourceClose"),this._mediaSource&&null!=this.e&&(this._mediaSource.removeEventListener("sourceopen",this.e.onSourceOpen),this._mediaSource.removeEventListener("sourceended",this.e.onSourceEnded),this._mediaSource.removeEventListener("sourceclose",this.e.onSourceClose))}},{key:"_hasPendingSegments",value:function(){var ps=this._pendingSegments;return 0<ps.video.length||0<ps.audio.length}},{key:"_hasPendingRemoveRanges",value:function(){var prr=this._pendingRemoveRanges;return 0<prr.video.length||0<prr.audio.length}},{key:"_onSourceBufferUpdateEnd",value:function(){this._requireSetMediaDuration?this._updateMediaSourceDuration():this._hasPendingRemoveRanges()?this._doRemoveRanges():this._hasPendingSegments()?this._doAppendSegments():this._hasPendingEos&&this.endOfStream(),this._emitter.emit(_mseEvents.default.UPDATE_END)}},{key:"_onSourceBufferError",value:function(e){_logger.default.e(this.TAG,"SourceBuffer Error: ".concat(e))}}]),MSEController}();_exports.default=MSEController}); |