diff --git a/src/playlist.js b/src/playlist.js index 496a7eb0f..e27ec5454 100644 --- a/src/playlist.js +++ b/src/playlist.js @@ -372,16 +372,16 @@ export const seekable = function(playlist, expired, liveEdgePadding) { * @param {number} options.currentTime The number of seconds since the earliest * possible position to determine the containing segment for * @param {number} options.startTime the time when the segment/part starts - * @param {number} options.segmentIndex the segment index to start looking at. - * @param {number?} [options.partIndex] the part index to look at within the segment. + * @param {number} options.startingSegmentIndex the segment index to start looking at. + * @param {number?} [options.startingPartIndex] the part index to look at within the segment. * * @return {Object} an object with partIndex, segmentIndex, and startTime. */ export const getMediaInfoForTime = function({ playlist, currentTime, - segmentIndex, - partIndex, + startingSegmentIndex, + startingPartIndex, startTime }) { @@ -393,12 +393,12 @@ export const getMediaInfoForTime = function({ for (let i = 0; i < partsAndSegments.length; i++) { const partAndSegment = partsAndSegments[i]; - if (segmentIndex !== partAndSegment.segmentIndex) { + if (startingSegmentIndex !== partAndSegment.segmentIndex) { continue; } // skip this if part index does not match. - if (typeof partIndex === 'number' && typeof partAndSegment.partIndex === 'number' && partIndex !== partAndSegment.partIndex) { + if (typeof startingPartIndex === 'number' && typeof partAndSegment.partIndex === 'number' && startingPartIndex !== partAndSegment.partIndex) { continue; } diff --git a/src/segment-loader.js b/src/segment-loader.js index dcde7c810..c73c076da 100644 --- a/src/segment-loader.js +++ b/src/segment-loader.js @@ -1399,8 +1399,8 @@ export default class SegmentLoader extends videojs.EventTarget { const {segmentIndex, startTime, partIndex} = Playlist.getMediaInfoForTime({ playlist: this.playlist_, currentTime: this.fetchAtBuffer_ ? bufferedEnd : this.currentTime_(), - partIndex: this.syncPoint_.partIndex, - segmentIndex: this.syncPoint_.segmentIndex, + startingPartIndex: this.syncPoint_.partIndex, + startingSegmentIndex: this.syncPoint_.segmentIndex, startTime: this.syncPoint_.time }); diff --git a/src/sync-controller.js b/src/sync-controller.js index 58d2fa99f..27f48f73b 100644 --- a/src/sync-controller.js +++ b/src/sync-controller.js @@ -38,6 +38,8 @@ export const syncPointStrategies = [ currentTime = currentTime || 0; for (let i = 0; i < partsAndSegments.length; i++) { + // start from the end and loop backwards for live + // or start from the front and loop forwards for non-live const index = (playlist.endList || currentTime === 0) ? i : partsAndSegments.length - (i + 1); const partAndSegment = partsAndSegments[index]; const segment = partAndSegment.segment; @@ -89,6 +91,8 @@ export const syncPointStrategies = [ const partsAndSegments = getPartsAndSegments(playlist); for (let i = 0; i < partsAndSegments.length; i++) { + // start from the end and loop backwards for live + // or start from the front and loop forwards for non-live const index = (playlist.endList || currentTime === 0) ? i : partsAndSegments.length - (i + 1); const partAndSegment = partsAndSegments[index]; const segment = partAndSegment.segment; diff --git a/test/playlist.test.js b/test/playlist.test.js index 35297a550..bcb95ffb2 100644 --- a/test/playlist.test.js +++ b/test/playlist.test.js @@ -1001,8 +1001,8 @@ QUnit.module('Playlist', function() { this.defaults = { playlist: media, currentTime: -1, - segmentIndex: 0, - partIndex: null, + startingSegmentIndex: 0, + startingPartIndex: null, startTime: 0 }; @@ -1067,8 +1067,8 @@ QUnit.module('Playlist', function() { this.defaults = { playlist: media, currentTime: 2.1, - segmentIndex: 0, - partIndex: null, + startingSegmentIndex: 0, + startingPartIndex: null, startTime: 0 }; @@ -1079,61 +1079,61 @@ QUnit.module('Playlist', function() { '1 away 2 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 4.1, segmentIndex: 1, startTime: 2}), + this.getMediaInfoForTime({currentTime: 4.1, startingSegmentIndex: 1, startTime: 2}), {segmentIndex: 2, startTime: 4, partIndex: null}, '1 away 3 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 6.1, segmentIndex: 2, startTime: 4}), + this.getMediaInfoForTime({currentTime: 6.1, startingSegmentIndex: 2, startTime: 4}), {segmentIndex: 3, startTime: 6, partIndex: null}, '1 away 4 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 8.1, segmentIndex: 3, startTime: 6}), + this.getMediaInfoForTime({currentTime: 8.1, startingSegmentIndex: 3, startTime: 6}), {segmentIndex: 4, startTime: 8, partIndex: null}, '1 away 5 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 10.1, segmentIndex: 4, startTime: 8}), + this.getMediaInfoForTime({currentTime: 10.1, startingSegmentIndex: 4, startTime: 8}), {segmentIndex: 5, startTime: 10, partIndex: null}, '1 away 6 is correct' ); // 2 segments away assert.deepEqual( - this.getMediaInfoForTime({currentTime: 4.1, segmentIndex: 0, startTime: 0}), + this.getMediaInfoForTime({currentTime: 4.1, startingSegmentIndex: 0, startTime: 0}), {segmentIndex: 2, startTime: 4, partIndex: null}, '2 away 3 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 6.1, segmentIndex: 1, startTime: 2}), + this.getMediaInfoForTime({currentTime: 6.1, startingSegmentIndex: 1, startTime: 2}), {segmentIndex: 3, startTime: 6, partIndex: null}, '2 away 4 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 8.1, segmentIndex: 2, startTime: 4}), + this.getMediaInfoForTime({currentTime: 8.1, startingSegmentIndex: 2, startTime: 4}), {segmentIndex: 4, startTime: 8, partIndex: null}, '2 away 5 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 10.1, segmentIndex: 3, startTime: 6}), + this.getMediaInfoForTime({currentTime: 10.1, startingSegmentIndex: 3, startTime: 6}), {segmentIndex: 5, startTime: 10, partIndex: null}, '2 away 6 is correct' ); // 3 segments away assert.deepEqual( - this.getMediaInfoForTime({currentTime: 6.1, segmentIndex: 0, startTime: 0}), + this.getMediaInfoForTime({currentTime: 6.1, startingSegmentIndex: 0, startTime: 0}), {segmentIndex: 3, startTime: 6, partIndex: null}, '3 away 4 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 8.1, segmentIndex: 1, startTime: 2}), + this.getMediaInfoForTime({currentTime: 8.1, startingSegmentIndex: 1, startTime: 2}), {segmentIndex: 4, startTime: 8, partIndex: null}, '3 away 5 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 10.1, segmentIndex: 2, startTime: 4}), + this.getMediaInfoForTime({currentTime: 10.1, startingSegmentIndex: 2, startTime: 4}), {segmentIndex: 5, startTime: 10, partIndex: null}, '3 away 6 is correct' ); @@ -1168,74 +1168,74 @@ QUnit.module('Playlist', function() { this.defaults = { playlist: media, currentTime: 2.1, - segmentIndex: 0, - partIndex: null, + startingSegmentIndex: 0, + startingPartIndex: null, startTime: 0 }; // 1 segment away assert.deepEqual( - this.getMediaInfoForTime({currentTime: 0, segmentIndex: 1, startTime: 2}), + this.getMediaInfoForTime({currentTime: 0, startingSegmentIndex: 1, startTime: 2}), {segmentIndex: 0, startTime: 0, partIndex: null}, '1 away 1 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 2.1, segmentIndex: 2, startTime: 4}), + this.getMediaInfoForTime({currentTime: 2.1, startingSegmentIndex: 2, startTime: 4}), {segmentIndex: 1, startTime: 2, partIndex: null}, '1 away 2 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 4.1, segmentIndex: 3, startTime: 6}), + this.getMediaInfoForTime({currentTime: 4.1, startingSegmentIndex: 3, startTime: 6}), {segmentIndex: 2, startTime: 4, partIndex: null}, '1 away 3 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 6.1, segmentIndex: 4, startTime: 8}), + this.getMediaInfoForTime({currentTime: 6.1, startingSegmentIndex: 4, startTime: 8}), {segmentIndex: 3, startTime: 6, partIndex: null}, '1 away 4 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 8.1, segmentIndex: 5, startTime: 10}), + this.getMediaInfoForTime({currentTime: 8.1, startingSegmentIndex: 5, startTime: 10}), {segmentIndex: 4, startTime: 8, partIndex: null}, '1 away 5 is correct' ); // 2 segments away assert.deepEqual( - this.getMediaInfoForTime({currentTime: 0, segmentIndex: 2, startTime: 4}), + this.getMediaInfoForTime({currentTime: 0, startingSegmentIndex: 2, startTime: 4}), {segmentIndex: 0, startTime: 0, partIndex: null}, '2 away 1 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 2.1, segmentIndex: 3, startTime: 6}), + this.getMediaInfoForTime({currentTime: 2.1, startingSegmentIndex: 3, startTime: 6}), {segmentIndex: 1, startTime: 2, partIndex: null}, '2 away 2 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 4.1, segmentIndex: 4, startTime: 8}), + this.getMediaInfoForTime({currentTime: 4.1, startingSegmentIndex: 4, startTime: 8}), {segmentIndex: 2, startTime: 4, partIndex: null}, '2 away 3 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 6.1, segmentIndex: 5, startTime: 10}), + this.getMediaInfoForTime({currentTime: 6.1, startingSegmentIndex: 5, startTime: 10}), {segmentIndex: 3, startTime: 6, partIndex: null}, '2 away 4 is correct' ); // 3 segments away assert.deepEqual( - this.getMediaInfoForTime({currentTime: 0, segmentIndex: 3, startTime: 6}), + this.getMediaInfoForTime({currentTime: 0, startingSegmentIndex: 3, startTime: 6}), {segmentIndex: 0, startTime: 0, partIndex: null}, '3 away 1 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 2.1, segmentIndex: 4, startTime: 8}), + this.getMediaInfoForTime({currentTime: 2.1, startingSegmentIndex: 4, startTime: 8}), {segmentIndex: 1, startTime: 2, partIndex: null}, '3 away 2 is correct' ); assert.deepEqual( - this.getMediaInfoForTime({currentTime: 4.1, segmentIndex: 5, startTime: 10}), + this.getMediaInfoForTime({currentTime: 4.1, startingSegmentIndex: 5, startTime: 10}), {segmentIndex: 2, startTime: 4, partIndex: null}, '3 away 3 is correct' ); @@ -1264,8 +1264,8 @@ QUnit.module('Playlist', function() { this.defaults = { playlist: media, currentTime: 0, - segmentIndex: 0, - partIndex: null, + startingSegmentIndex: 0, + startingPartIndex: null, startTime: 0 }; @@ -1310,8 +1310,8 @@ QUnit.module('Playlist', function() { this.defaults = { playlist: media, currentTime: 0, - segmentIndex: 0, - partIndex: null, + startingSegmentIndex: 0, + startingPartIndex: null, startTime: 0 }; @@ -1394,8 +1394,8 @@ QUnit.module('Playlist', function() { this.defaults = { playlist: media, currentTime: 0, - segmentIndex: 0, - partIndex: null, + startingSegmentIndex: 0, + startingPartIndex: null, startTime: 0 }; diff --git a/test/sync-controller.test.js b/test/sync-controller.test.js index e73df8116..4650395c4 100644 --- a/test/sync-controller.test.js +++ b/test/sync-controller.test.js @@ -246,30 +246,20 @@ QUnit.test('ProgramDateTime strategy finds nearest llhls sync point', function(a this.syncController.setDateTimeMappingForStart(playlist); - const newPlaylist = playlistWithDuration(200, {llhls: true}); - - syncPoint = strategy.run(this.syncController, newPlaylist, duration, timeline); - - assert.equal(syncPoint, null, 'no syncpoint when datetimeObject not set on playlist'); - - newPlaylist.segments.forEach((segment, index) => { - segment.dateTimeObject = new Date(2012, 11, 12, 12, 12, 22 + (index * 10)); - }); - - syncPoint = strategy.run(this.syncController, newPlaylist, duration, timeline, 194); + syncPoint = strategy.run(this.syncController, playlist, duration, timeline, 194); assert.deepEqual(syncPoint, { time: 192, - segmentIndex: 18, + segmentIndex: 19, partIndex: 1 }, 'syncpoint found for ProgramDateTime'); - syncPoint = strategy.run(this.syncController, newPlaylist, duration, timeline, 204); + syncPoint = strategy.run(this.syncController, playlist, duration, timeline, 204); assert.deepEqual(syncPoint, { - time: 202, + time: 198, segmentIndex: 19, - partIndex: 1 + partIndex: 4 }, 'syncpoint found for ProgramDateTime'); });