]> git.immae.eu Git - github/Chocobozzz/PeerTube.git/blobdiff - client/src/app/+videos/+video-watch/video-watch-playlist.component.ts
Merge remote-tracking branch 'weblate/develop' into develop
[github/Chocobozzz/PeerTube.git] / client / src / app / +videos / +video-watch / video-watch-playlist.component.ts
index 519ce29741921048470b18e423f2e30e451e714b..0a4d6bfd11c66d2dd6a9e0852a28a182b332e167 100644 (file)
@@ -1,10 +1,10 @@
-import { Component, Input } from '@angular/core'
+
+import { Component, EventEmitter, Input, Output } from '@angular/core'
 import { Router } from '@angular/router'
 import { AuthService, ComponentPagination, LocalStorageService, Notifier, SessionStorageService, UserService } from '@app/core'
-import { peertubeLocalStorage, peertubeSessionStorage } from '@root-helpers/peertube-web-storage'
 import { VideoPlaylist, VideoPlaylistElement, VideoPlaylistService } from '@app/shared/shared-video-playlist'
-import { I18n } from '@ngx-translate/i18n-polyfill'
-import { VideoDetails, VideoPlaylistPrivacy } from '@shared/models'
+import { peertubeLocalStorage, peertubeSessionStorage } from '@root-helpers/peertube-web-storage'
+import { VideoPlaylistPrivacy } from '@shared/models'
 
 @Component({
   selector: 'my-video-watch-playlist',
@@ -15,9 +15,10 @@ export class VideoWatchPlaylistComponent {
   static LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST = 'auto_play_video_playlist'
   static SESSION_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST = 'loop_playlist'
 
-  @Input() video: VideoDetails
   @Input() playlist: VideoPlaylist
 
+  @Output() videoFound = new EventEmitter<string>()
+
   playlistElements: VideoPlaylistElement[] = []
   playlistPagination: ComponentPagination = {
     currentPage: 1,
@@ -30,13 +31,13 @@ export class VideoWatchPlaylistComponent {
   loopPlaylist: boolean
   loopPlaylistSwitchText = ''
   noPlaylistVideos = false
-  currentPlaylistPosition = 1
+
+  currentPlaylistPosition: number
 
   constructor (
     private userService: UserService,
     private auth: AuthService,
     private notifier: Notifier,
-    private i18n: I18n,
     private videoPlaylist: VideoPlaylistService,
     private localStorageService: LocalStorageService,
     private sessionStorageService: SessionStorageService,
@@ -46,6 +47,7 @@ export class VideoWatchPlaylistComponent {
     this.autoPlayNextVideoPlaylist = this.auth.isLoggedIn()
       ? this.auth.getUser().autoPlayNextVideoPlaylist
       : this.localStorageService.getItem(VideoWatchPlaylistComponent.LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST) !== 'false'
+
     this.setAutoPlayNextVideoPlaylistSwitchText()
 
     // defaults to false
@@ -53,12 +55,12 @@ export class VideoWatchPlaylistComponent {
     this.setLoopPlaylistSwitchText()
   }
 
-  onPlaylistVideosNearOfBottom () {
+  onPlaylistVideosNearOfBottom (position?: number) {
     // Last page
     if (this.playlistPagination.totalItems <= (this.playlistPagination.currentPage * this.playlistPagination.itemsPerPage)) return
 
     this.playlistPagination.currentPage += 1
-    this.loadPlaylistElements(this.playlist,false)
+    this.loadPlaylistElements(this.playlist, false, position)
   }
 
   onElementRemoved (playlistElement: VideoPlaylistElement) {
@@ -85,26 +87,26 @@ export class VideoWatchPlaylistComponent {
     return this.playlist.privacy.id === VideoPlaylistPrivacy.PUBLIC
   }
 
-  loadPlaylistElements (playlist: VideoPlaylist, redirectToFirst = false) {
+  loadPlaylistElements (playlist: VideoPlaylist, redirectToFirst = false, position?: number) {
     this.videoPlaylist.getPlaylistVideos(playlist.uuid, this.playlistPagination)
         .subscribe(({ total, data }) => {
           this.playlistElements = this.playlistElements.concat(data)
           this.playlistPagination.totalItems = total
 
-          const firstAvailableVideos = this.playlistElements.find(e => !!e.video)
-          if (!firstAvailableVideos) {
+          const firstAvailableVideo = this.playlistElements.find(e => !!e.video)
+          if (!firstAvailableVideo) {
             this.noPlaylistVideos = true
             return
           }
 
-          this.updatePlaylistIndex(this.video)
+          if (position) this.updatePlaylistIndex(position)
 
           if (redirectToFirst) {
             const extras = {
               queryParams: {
-                start: firstAvailableVideos.startTimestamp,
-                stop: firstAvailableVideos.stopTimestamp,
-                videoId: firstAvailableVideos.video.uuid
+                start: firstAvailableVideo.startTimestamp,
+                stop: firstAvailableVideo.stopTimestamp,
+                playlistPosition: firstAvailableVideo.position
               },
               replaceUrl: true
             }
@@ -113,45 +115,71 @@ export class VideoWatchPlaylistComponent {
         })
   }
 
-  updatePlaylistIndex (video: VideoDetails) {
-    if (this.playlistElements.length === 0 || !video) return
+  updatePlaylistIndex (position: number) {
+    if (this.playlistElements.length === 0 || !position) return
+
+    // Handle the reverse index
+    if (position < 0) position = this.playlist.videosLength + position + 1
 
     for (const playlistElement of this.playlistElements) {
-      if (playlistElement.video && playlistElement.video.id === video.id) {
+      // >= if the previous videos were not valid
+      if (playlistElement.video && playlistElement.position >= position) {
         this.currentPlaylistPosition = playlistElement.position
+
+        this.videoFound.emit(playlistElement.video.uuid)
+
+        setTimeout(() => {
+          document.querySelector('.element-' + this.currentPlaylistPosition).scrollIntoView(false)
+        }, 0)
+
         return
       }
     }
 
     // Load more videos to find our video
-    this.onPlaylistVideosNearOfBottom()
+    this.onPlaylistVideosNearOfBottom(position)
   }
 
-  findNextPlaylistVideo (position = this.currentPlaylistPosition): VideoPlaylistElement {
-    if (this.currentPlaylistPosition >= this.playlistPagination.totalItems) {
-      // we have reached the end of the playlist: either loop or stop
-      if (this.loopPlaylist) {
-        this.currentPlaylistPosition = position = 0
-      } else {
-        return
-      }
-    }
+  navigateToPreviousPlaylistVideo () {
+    const previous = this.findPlaylistVideo(this.currentPlaylistPosition - 1, 'previous')
+    if (!previous) return
 
-    const next = this.playlistElements.find(e => e.position === position)
+    const start = previous.startTimestamp
+    const stop = previous.stopTimestamp
+    this.router.navigate([],{ queryParams: { playlistPosition: previous.position, start, stop } })
+  }
 
-    if (!next || !next.video) {
-      return this.findNextPlaylistVideo(position + 1)
+  findPlaylistVideo (position: number, type: 'previous' | 'next'): VideoPlaylistElement {
+    if (
+      (type === 'next' && position > this.playlistPagination.totalItems) ||
+      (type === 'previous' && position < 1)
+    ) {
+      // End of the playlist: end the recursion if we're not in the loop mode
+      if (!this.loopPlaylist) return
+
+      // Loop mode
+      position = type === 'previous'
+        ? this.playlistPagination.totalItems
+        : 1
     }
 
-    return next
+    const found = this.playlistElements.find(e => e.position === position)
+    if (found && found.video) return found
+
+    const newPosition = type === 'previous'
+      ? position - 1
+      : position + 1
+
+    return this.findPlaylistVideo(newPosition, type)
   }
 
   navigateToNextPlaylistVideo () {
-    const next = this.findNextPlaylistVideo(this.currentPlaylistPosition + 1)
+    const next = this.findPlaylistVideo(this.currentPlaylistPosition + 1, 'next')
     if (!next) return
+
     const start = next.startTimestamp
     const stop = next.stopTimestamp
-    this.router.navigate([],{ queryParams: { videoId: next.video.uuid, start, stop } })
+    this.router.navigate([],{ queryParams: { playlistPosition: next.position, start, stop } })
   }
 
   switchAutoPlayNextVideoPlaylist () {
@@ -189,13 +217,13 @@ export class VideoWatchPlaylistComponent {
 
   private setAutoPlayNextVideoPlaylistSwitchText () {
     this.autoPlayNextVideoPlaylistSwitchText = this.autoPlayNextVideoPlaylist
-      ? this.i18n('Stop autoplaying next video')
-      : this.i18n('Autoplay next video')
+      ? $localize`Stop autoplaying next video`
+      : $localize`Autoplay next video`
   }
 
   private setLoopPlaylistSwitchText () {
     this.loopPlaylistSwitchText = this.loopPlaylist
-      ? this.i18n('Stop looping playlist videos')
-      : this.i18n('Loop playlist videos')
+      ? $localize`Stop looping playlist videos`
+      : $localize`Loop playlist videos`
   }
 }