Skip to content

Commit

Permalink
feat: Add support for ManagedMediaSource 'startstreaming' and 'endstr…
Browse files Browse the repository at this point in the history
…eam' event handling (#1542)
  • Loading branch information
alex-barstow authored Oct 9, 2024
1 parent bfc17b4 commit ae1ae70
Show file tree
Hide file tree
Showing 2 changed files with 58 additions and 0 deletions.
22 changes: 22 additions & 0 deletions src/playlist-controller.js
Original file line number Diff line number Diff line change
Expand Up @@ -215,6 +215,7 @@ export class PlaylistController extends videojs.EventTarget {
// Airplay source not yet implemented. Remote playback must be disabled.
this.tech_.el_.disableRemotePlayback = true;
this.mediaSource = new window.ManagedMediaSource();

videojs.log('Using ManagedMediaSource');
} else if (window.MediaSource) {
this.mediaSource = new window.MediaSource();
Expand All @@ -223,12 +224,16 @@ export class PlaylistController extends videojs.EventTarget {
this.handleDurationChange_ = this.handleDurationChange_.bind(this);
this.handleSourceOpen_ = this.handleSourceOpen_.bind(this);
this.handleSourceEnded_ = this.handleSourceEnded_.bind(this);
this.load = this.load.bind(this);
this.pause = this.pause.bind(this);

this.mediaSource.addEventListener('durationchange', this.handleDurationChange_);

// load the media source into the player
this.mediaSource.addEventListener('sourceopen', this.handleSourceOpen_);
this.mediaSource.addEventListener('sourceended', this.handleSourceEnded_);
this.mediaSource.addEventListener('startstreaming', this.load);
this.mediaSource.addEventListener('endstreaming', this.pause);
// we don't have to handle sourceclose since dispose will handle termination of
// everything, and the MediaSource should not be detached without a proper disposal

Expand Down Expand Up @@ -1056,14 +1061,31 @@ export class PlaylistController extends videojs.EventTarget {
*/
load() {
this.mainSegmentLoader_.load();

if (this.mediaTypes_.AUDIO.activePlaylistLoader) {
this.audioSegmentLoader_.load();
}

if (this.mediaTypes_.SUBTITLES.activePlaylistLoader) {
this.subtitleSegmentLoader_.load();
}
}

/**
* Call pause on our SegmentLoaders
*/
pause() {
this.mainSegmentLoader_.pause();

if (this.mediaTypes_.AUDIO.activePlaylistLoader) {
this.audioSegmentLoader_.pause();
}

if (this.mediaTypes_.SUBTITLES.activePlaylistLoader) {
this.subtitleSegmentLoader_.pause();
}
}

/**
* Re-tune playback quality level for the current player
* conditions. This method will perform destructive actions like removing
Expand Down
36 changes: 36 additions & 0 deletions test/playlist-controller.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -7693,3 +7693,39 @@ QUnit.test('uses ManagedMediaSource only when opted in', function(assert) {
mmsSpy.restore();
mms.restore();
});

QUnit.test('ManagedMediaSource startstreaming and endstreaming events start and pause segment loading respectively', function(assert) {
const mms = useFakeManagedMediaSource();
const options = {
src: 'test.m3u8',
tech: this.player.tech_,
player_: this.player,
experimentalUseMMS: true
};

const controller = new PlaylistController(options);

controller.mediaTypes_.AUDIO.activePlaylistLoader = {};
controller.mediaTypes_.SUBTITLES.activePlaylistLoader = {};

const mainLoadSpy = sinon.spy(controller.mainSegmentLoader_, 'load');
const audioLoadSpy = sinon.spy(controller.audioSegmentLoader_, 'load');
const subtitleLoadSpy = sinon.spy(controller.subtitleSegmentLoader_, 'load');
const mainPauseSpy = sinon.spy(controller.mainSegmentLoader_, 'pause');
const audioPauseSpy = sinon.spy(controller.audioSegmentLoader_, 'pause');
const subtitlePauseSpy = sinon.spy(controller.subtitleSegmentLoader_, 'pause');

controller.mediaSource.trigger('startstreaming');

assert.ok(mainLoadSpy.calledOnce, 'Segment loading started on startstreaming event');
assert.ok(audioLoadSpy.calledOnce, 'Audio segment loading started on startstreaming event');
assert.ok(subtitleLoadSpy.calledOnce, 'Subtitle segment loading started on startstreaming event');

controller.mediaSource.trigger('endstreaming');

assert.ok(mainPauseSpy.calledOnce, 'Main segment loading paused on endstreaming event');
assert.ok(audioPauseSpy.calledOnce, 'Audio segment loading paused on endstreaming event');
assert.ok(subtitlePauseSpy.calledOnce, 'Subtitle segment loading paused on endstreaming event');

mms.restore();
});

0 comments on commit ae1ae70

Please sign in to comment.