Skip to content

Commit

Permalink
Treat absent timeShiftBufferDepth as infinity.
Browse files Browse the repository at this point in the history
This patch also enables presentations to start in live mode
and end in VOD mode.

Issue #351

Change-Id: Idc0ad0c69887d61d080f844ef388222d1228a535
  • Loading branch information
Timothy Drews committed May 2, 2016
1 parent bc17162 commit 294bcca
Show file tree
Hide file tree
Showing 7 changed files with 96 additions and 82 deletions.
32 changes: 13 additions & 19 deletions lib/dash/dash_parser.js
Original file line number Diff line number Diff line change
Expand Up @@ -421,24 +421,16 @@ shaka.dash.DashParser.prototype.parseManifest_ =
if (this.manifest_) {
presentationTimeline = this.manifest_.presentationTimeline;
} else {
if (segmentAvailabilityDuration) {
// If there's a segment availability window then the presentation is
// live.
if (presentationStartTime != null) {
// Offset the start time by @suggestedPresentationDelay. This has the
// effect of making the segments become available later than they
// actually are, so it causes a delay. Note that the DASH spec
// recommends that a default @suggestedPresentationDelay be used when
// one is not explicitly specified.
presentationStartTime +=
suggestedPresentationDelay != null ?
suggestedPresentationDelay :
shaka.dash.DashParser.DEFAULT_SUGGESTED_PRESENTATION_DELAY_;
} else {
presentationStartTime = 0;
}
} else {
presentationStartTime = null;
if (presentationStartTime != null) {
// Offset the start time by @suggestedPresentationDelay. This has the
// effect of making the segments become available later than they
// actually are, so it causes a delay. Note that the DASH spec
// recommends that a default @suggestedPresentationDelay be used when
// one is not explicitly specified.
presentationStartTime +=
suggestedPresentationDelay != null ?
suggestedPresentationDelay :
shaka.dash.DashParser.DEFAULT_SUGGESTED_PRESENTATION_DELAY_;
}
presentationTimeline =
new shaka.media.PresentationTimeline(presentationStartTime);
Expand Down Expand Up @@ -468,7 +460,9 @@ shaka.dash.DashParser.prototype.parseManifest_ =
presentationTimeline.setDuration(duration || Number.POSITIVE_INFINITY);
presentationTimeline.setClockOffset(offset);
presentationTimeline.setSegmentAvailabilityDuration(
segmentAvailabilityDuration);
segmentAvailabilityDuration != null ?
segmentAvailabilityDuration :
Number.POSITIVE_INFINITY);

if (!this.manifest_) {
// Use @maxSegmentDuration to override smaller, derived values.
Expand Down
10 changes: 5 additions & 5 deletions lib/media/playhead.js
Original file line number Diff line number Diff line change
Expand Up @@ -329,12 +329,12 @@ shaka.media.Playhead.prototype.onSeeking_ = function() {
* @private
*/
shaka.media.Playhead.prototype.reposition_ = function(currentTime) {
var availabilityDuration = this.timeline_.getSegmentAvailabilityDuration();
var start = this.timeline_.getEarliestStart();
var end = this.timeline_.getSegmentAvailabilityEnd();
var timeline = this.timeline_;
var start = timeline.getEarliestStart();
var end = timeline.getSegmentAvailabilityEnd();

if (availabilityDuration == null ||
availabilityDuration == Number.POSITIVE_INFINITY) {
if (!timeline.isLive() ||
timeline.getSegmentAvailabilityDuration() == Number.POSITIVE_INFINITY) {
// If the presentation is live but has an infinite segment availability
// duration then we can treat it as VOD since the start of the seek range
// is not moving.
Expand Down
33 changes: 19 additions & 14 deletions lib/media/presentation_timeline.js
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,8 @@ shaka.media.PresentationTimeline = function(presentationStartTime) {
/** @private {number} */
this.duration_ = Number.POSITIVE_INFINITY;

/** @private {?number} */
this.segmentAvailabilityDuration_ = null;
/** @private {number} */
this.segmentAvailabilityDuration_ = Number.POSITIVE_INFINITY;

/** @private {?number} */
this.maxSegmentDuration_ = 1;
Expand Down Expand Up @@ -93,8 +93,7 @@ shaka.media.PresentationTimeline.prototype.setClockOffset = function(offset) {
* presentation has a 5 minute DVR window and your segments are 10 seconds long
* then the segment availability duration should be 4 minutes and 50 seconds.
*
* @return {?number} The presentation's segment availability duration.
* Always returns null for video-on-demand, and never returns null for live.
* @return {number} The presentation's segment availability duration.
*/
shaka.media.PresentationTimeline.prototype.getSegmentAvailabilityDuration =
function() {
Expand All @@ -104,17 +103,15 @@ shaka.media.PresentationTimeline.prototype.getSegmentAvailabilityDuration =

/**
* Sets the presentation's segment availability duration. The segment
* availability duration can only be updated for live.
* availability duration should only be set for live.
*
* @param {?number} segmentAvailabilityDuration The presentation's new segment
* @param {number} segmentAvailabilityDuration The presentation's new segment
* availability duration in seconds.
*/
shaka.media.PresentationTimeline.prototype.setSegmentAvailabilityDuration =
function(segmentAvailabilityDuration) {
goog.asserts.assert(
(segmentAvailabilityDuration === null) ||
(segmentAvailabilityDuration >= 0),
'segmentAvailabilityDuration must be null or >= 0');
goog.asserts.assert(segmentAvailabilityDuration >= 0,
'segmentAvailabilityDuration must be >= 0');
this.segmentAvailabilityDuration_ = segmentAvailabilityDuration;
};

Expand Down Expand Up @@ -167,6 +164,16 @@ shaka.media.PresentationTimeline.prototype.notifyMaxSegmentDuration = function(
};


/**
* @return {boolean} True if the presentation is live; otherwise, return
* false.
*/
shaka.media.PresentationTimeline.prototype.isLive = function() {
return this.duration_ == Number.POSITIVE_INFINITY ||
this.segmentAvailabilityDuration_ < Number.POSITIVE_INFINITY;
};


/**
* Gets the presentation's current earliest, available timestamp. This value
* may be greater than the presentation's current segment availability start
Expand All @@ -193,10 +200,8 @@ shaka.media.PresentationTimeline.prototype.getEarliestStart = function() {
*/
shaka.media.PresentationTimeline.prototype.getSegmentAvailabilityStart =
function() {
if (this.presentationStartTime_ == null ||
this.segmentAvailabilityDuration_ == Number.POSITIVE_INFINITY) {
if (this.segmentAvailabilityDuration_ == Number.POSITIVE_INFINITY)
return 0;
}

return Math.max(
0, this.getSegmentAvailabilityEnd() - this.segmentAvailabilityDuration_);
Expand All @@ -213,7 +218,7 @@ shaka.media.PresentationTimeline.prototype.getSegmentAvailabilityStart =
*/
shaka.media.PresentationTimeline.prototype.getSegmentAvailabilityEnd =
function() {
if (this.presentationStartTime_ == null)
if (this.presentationStartTime_ == null || !this.isLive())
return this.duration_;

return Math.min(this.getLiveEdge_(), this.duration_);
Expand Down
8 changes: 3 additions & 5 deletions lib/player.js
Original file line number Diff line number Diff line change
Expand Up @@ -629,11 +629,9 @@ shaka.Player.prototype.getNetworkingEngine = function() {
* @export
*/
shaka.Player.prototype.isLive = function() {
if (!this.manifest_) return false;

// If the presentation has a segment availability window then it's live.
var timeline = this.manifest_.presentationTimeline;
return timeline.getSegmentAvailabilityDuration() != null;
return this.manifest_ ?
this.manifest_.presentationTimeline.isLive() :
false;
};


Expand Down
4 changes: 4 additions & 0 deletions test/playhead_unit.js
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ describe('Playhead', function() {
}
});

timeline.isLive.and.returnValue(false);
timeline.getEarliestStart.and.returnValue(5);
timeline.getSegmentAvailabilityStart.and.returnValue(5);
timeline.getSegmentAvailabilityEnd.and.returnValue(60);
Expand Down Expand Up @@ -174,6 +175,7 @@ describe('Playhead', function() {
}
};

timeline.isLive.and.returnValue(true);
timeline.getEarliestStart.and.returnValue(5);
timeline.getSegmentAvailabilityStart.and.returnValue(5);
timeline.getSegmentAvailabilityEnd.and.returnValue(60);
Expand Down Expand Up @@ -327,6 +329,7 @@ describe('Playhead', function() {
}
};

timeline.isLive.and.returnValue(false);
timeline.getEarliestStart.and.returnValue(5);
timeline.getSegmentAvailabilityStart.and.returnValue(5);
timeline.getSegmentAvailabilityEnd.and.returnValue(60);
Expand Down Expand Up @@ -382,6 +385,7 @@ describe('Playhead', function() {
setDuration: jasmine.createSpy('setDuration'),
getSegmentAvailabilityDuration:
jasmine.createSpy('getSegmentAvailabilityDuration'),
isLive: jasmine.createSpy('isLive'),
getEarliestStart: jasmine.createSpy('getEarliestStart'),
getSegmentAvailabilityStart:
jasmine.createSpy('getSegmentAvailabilityStart'),
Expand Down
Loading

0 comments on commit 294bcca

Please sign in to comment.