videogular2 icon indicating copy to clipboard operation
videogular2 copied to clipboard

Add subtitle from remote source

Open pirasalbe opened this issue 6 years ago • 1 comments

Description

Hi, I'm trying to add a subtitle track programmatically. In my app the user select a subtitle from a list and I should add that remote subtitle track using the link provided.

Expected Behavior

I should be able to add subtitles track from a remote link (such as http://static.videogular.com/assets/subs/pale-blue-dot.vtt) with api or in html on user interaction.

Actual Behavior

I cannot show or hide a subtitle track programmatically.

Steps to Reproduce

The idea is that the user add one subititle downloading it directly from openSubtitle.

I create a default subtitle track (if none is set) that should be hidden, then when the user select a subtitle the function setSubtitle() is called, the default track should be modified and in the video I should see the track with the right language/description.

This is my TS

readonly language: SubtitleLanguage = new SubtitleLanguage('TMP', 'Temp');

getSubtitleLink(): SafeUrl {
    return this.subtitleLink;
  } 

getSubtitle(): Subtitle {
    return this.getCurrent().subtitle;
  }

getSubtitleLanguage(): SubtitleLanguage {
    if (!this.getSubtitle()) {
      return this.language;
    }

    return this.videoPlayerService.getSubtitle().language;
  }

/**
   * Sets subtitle of openSubtitles
   */
  setSubtitle(): void {
    if (!this.api) {
      return;
    }

    let mode: 'showing' | 'hidden' | 'disabled' = 'showing';
    if (this.getCurrent().hasSubtitle()) {
      // download a subtitle file from OS and set subtitle
      this.subtitlesService.downloadSubtitle(this.getSubtitle().downloadLink).then((sub: Blob) => {
        this.subtitleLink = this.sanitizer.bypassSecurityTrustUrl(URL.createObjectURL(sub));
      });
    } else {
      mode = 'hidden';
    }

    // show/hide subtitle tracks
    const textTracks: TextTrack[] = this.api.textTracks;
    for (const textTrack of textTracks) {
      textTrack.mode = mode;
    }
  }

And this is my HTML

<video #media class="video-player" [vgMedia]="media" id="singleVideo" preload="auto" [src]="getLink()" crossorigin>
    <track kind="subtitles" [label]="getSubtitleLanguage().name" [src]="getSubtitleLink()" [srclang]="getSubtitleLanguage().code" />
  </video>

pirasalbe avatar Mar 04 '19 07:03 pirasalbe

I had a similar problem when I tried to include tracks using a *ngFor on the track within the video element:

<video ...>
    <track ... *ngFor="let subFile of subFiles">
</video>

What I did was I added an id on the track selector element: <vg-track-selector **#trackSelector**></vg-track-selector>

In the typescript I added a ViewChild element for the track selector: @ViewChild('trackSelector') private trackSelector: any; // VgTrackSelector;

When the list of files with subtitles was fetched I then called onPlayerReady on trackSelector:

subFiles = await getSubtitles();
setTimeout(() => this.trackSelector.onPlayerReady());

The onPlayerReady function of the trackSelector determines all track elements within the video element and based upon the found track elements build the cc options shown to the user.

I hope this approach will also help in your case.

michastreppel avatar Aug 27 '19 09:08 michastreppel