Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add seekToLiveOffset attribute #923

Open
k-g-a opened this issue Jun 11, 2024 · 1 comment
Open

Add seekToLiveOffset attribute #923

k-g-a opened this issue Jun 11, 2024 · 1 comment

Comments

@k-g-a
Copy link
Contributor

k-g-a commented Jun 11, 2024

The problem

Currentrly, if we have a paused live stream and issue MEDIA_PLAY_REQUEST (i.e. via pressing play button), we are thrown straight to the end of seekable range:

const liveEdgeTime = stateMediator.mediaSeekable.get(stateOwners)?.[1];

if (notDvr && liveEdgeTime) {
  stateMediator.mediaCurrentTime.set(liveEdgeTime, stateOwners);
}

Unfortunatelly, this often causes a live stream to stall afterwards (not necessary immediately) due to the fact that it's playing too close to the edge - new video fragments just don't catch up in time, especially if poor network conditions are in place.

Proposed solution

The first thing that comes to mind is to use liveEdgeOffset within MEDIA_PLAY_REQUEST handler:

const liveEdgeTime = stateMediator.mediaSeekable.get(stateOwners)?.[1];

if (notDvr && liveEdgeTime) {
  const liveEdgeOffset = stateOwners.options.liveEdgeOffset ?? 0;
  stateMediator.mediaCurrentTime.set(liveEdgeTime - liveEdgeOffset, stateOwners);
}

But this may lead up to the other issue: if we are close enough to the moment of the next video segment arrival, as soon as it arrives we will fall back behind the liveEdgeOffset (i.e. duration/seekableEnd jump forward by the amount of the segment length). This will cause media-live-button to show that we are "not live" (i.e. become gray), but in a few moments the playback will catch up with liveEdgeOffset so the media-live-button becomes "live" (i.e. red). This process will continue to repeat and the media-live-button will "flicker". This is especially the case for segments with small durations (i.e. 3-5 seconds).

So, it's more reasonable to introduce another attribute called SEEK_TO_LIVE_OFFSET: 'seektoliveoffset' (with default of +this.getAttribute(Attributes.LIVE_EDGE_OFFSET) for example) and use it within MEDIA_PLAY_REQUEST nahdler.

In this case we could provide, for example of a 3-seconds video fragment length, the following values <media-controller liveedgeoffset="15" seektoliveoffset="11"> and get both: reliable media-live-button indication and enough segments ahead to overcome network problems.

In case this proposal is accepted, I can make a PR.

P.S.

We used to "hack" this behaviour in previous versions of media-chrome in the following way:

// in a react component wrapper
private refMediaController = (element: EnhancedMediaControllerWebComponent | null): void => {
    if (this.mediaControllerRef === element) {
      return;
    }

    if (this.mediaControllerRef) {
      this.mediaControllerRef.removeEventListener(
        MediaUIEvents.MEDIA_SEEK_TO_LIVE_REQUEST,
        this._handleMediaSeekToLiveRequestWithOffset
      );
    }

    if (element) {
      if (element._handleMediaSeekToLiveRequest) {
        element.removeEventListener(MediaUIEvents.MEDIA_SEEK_TO_LIVE_REQUEST, element._handleMediaSeekToLiveRequest);
      }
      element.addEventListener(MediaUIEvents.MEDIA_SEEK_TO_LIVE_REQUEST, this._handleMediaSeekToLiveRequestWithOffset);
    }

    this.mediaControllerRef = element;
  };

  private _handleMediaSeekToLiveRequestWithOffset = (): void => {
    const mediaControllerRef = this.mediaControllerRef;

    // some checks are omited for the sake of readability

    const endTime = seekable.end(seekable.length - 1);
    const seekToLiveOffset = this.props.seekToLiveOffset || 0;
    media.currentTime = endTime - seekToLiveOffset;
  };
@k-g-a
Copy link
Contributor Author

k-g-a commented Jun 11, 2024

Just found that there was (and still is, but unused) the NO_AUTO_SEEK_TO_LIVE: 'noautoseektolive' attribute.

It feels like it used to work, is it a regression? If so, I can file another issue about it.

k-g-a added a commit to k-g-a/media-chrome that referenced this issue Aug 16, 2024
This attribute is used within seek to live and play requests to offset the current time from the very end of the seekable range to prevent high chance of stalling afterwards. If not specified, defaults to liveedgeoffset.
k-g-a added a commit to k-g-a/media-chrome that referenced this issue Sep 17, 2024
This attribute is used within seek to live and play requests to offset the current time from the very end of the seekable range to prevent high chance of stalling afterwards. If not specified, defaults to liveedgeoffset.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant