add loop setting for playlists, and use sessionStorage
This commit is contained in:
parent
12f18b90ba
commit
88a7f93f8e
|
@ -1,5 +1,5 @@
|
|||
import { Component, OnInit } from '@angular/core'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-web-storage'
|
||||
import { Notifier } from '@app/core'
|
||||
import { SortMeta } from 'primeng/api'
|
||||
import { Job, JobType } from '../../../../../../shared/index'
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-web-storage'
|
||||
import { UserRight } from '../../../../../shared/models/users/user-right.enum'
|
||||
import { User as ServerUserModel } from '../../../../../shared/models/users/user.model'
|
||||
// Do not use the barrel (dependency loop)
|
||||
|
|
|
@ -12,7 +12,7 @@ import { RestExtractor } from '../../shared/rest/rest-extractor.service'
|
|||
import { AuthStatus } from './auth-status.model'
|
||||
import { AuthUser } from './auth-user.model'
|
||||
import { objectToUrlEncoded } from '@app/shared/misc/utils'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-web-storage'
|
||||
import { I18n } from '@ngx-translate/i18n-polyfill'
|
||||
import { Hotkey, HotkeysService } from 'angular2-hotkeys'
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import { map, shareReplay, switchMap, tap } from 'rxjs/operators'
|
||||
import { HttpClient } from '@angular/common/http'
|
||||
import { Inject, Injectable, LOCALE_ID } from '@angular/core'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-web-storage'
|
||||
import { Observable, of, ReplaySubject } from 'rxjs'
|
||||
import { getCompleteLocale, ServerConfig } from '../../../../../shared'
|
||||
import { environment } from '../../../environments/environment'
|
||||
|
|
|
@ -4,7 +4,7 @@ import { ServerService } from '@app/core/server'
|
|||
import { environment } from '../../../environments/environment'
|
||||
import { PluginService } from '@app/core/plugins/plugin.service'
|
||||
import { ServerConfigTheme } from '@shared/models'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-web-storage'
|
||||
|
||||
@Injectable()
|
||||
export class ThemeService {
|
||||
|
|
|
@ -26,6 +26,7 @@ const icons = {
|
|||
'cross': require('!!raw-loader?!../../../assets/images/global/cross.svg'),
|
||||
'validate': require('!!raw-loader?!../../../assets/images/global/validate.svg'),
|
||||
'tick': require('!!raw-loader?!../../../assets/images/global/tick.svg'),
|
||||
'repeat': require('!!raw-loader?!../../../assets/images/global/repeat.svg'),
|
||||
'dislike': require('!!raw-loader?!../../../assets/images/video/dislike.svg'),
|
||||
'support': require('!!raw-loader?!../../../assets/images/video/support.svg'),
|
||||
'like': require('!!raw-loader?!../../../assets/images/video/like.svg'),
|
||||
|
|
|
@ -42,12 +42,14 @@ class MemoryStorage {
|
|||
}
|
||||
|
||||
let peertubeLocalStorage: Storage
|
||||
let peertubeSessionStorage: Storage
|
||||
try {
|
||||
peertubeLocalStorage = localStorage
|
||||
peertubeSessionStorage = sessionStorage
|
||||
} catch (err) {
|
||||
const instance = new MemoryStorage()
|
||||
|
||||
peertubeLocalStorage = new Proxy(instance, {
|
||||
peertubeLocalStorage = sessionStorage = new Proxy(instance, {
|
||||
set: function (obj, prop: string | number, value) {
|
||||
if (MemoryStorage.prototype.hasOwnProperty(prop)) {
|
||||
instance[prop] = value
|
||||
|
@ -67,4 +69,7 @@ try {
|
|||
})
|
||||
}
|
||||
|
||||
export { peertubeLocalStorage }
|
||||
export {
|
||||
peertubeLocalStorage,
|
||||
peertubeSessionStorage
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-web-storage'
|
||||
import { LazyLoadEvent } from 'primeng/components/common/lazyloadevent'
|
||||
import { SortMeta } from 'primeng/components/common/sortmeta'
|
||||
import { RestPagination } from './rest-pagination'
|
||||
|
|
|
@ -24,6 +24,15 @@
|
|||
placement="bottom auto"
|
||||
container="body"
|
||||
></my-global-icon>
|
||||
|
||||
<my-global-icon
|
||||
iconName="repeat"
|
||||
[class.active]="loopPlaylist"
|
||||
(click)="switchLoopPlaylist()"
|
||||
[ngbTooltip]="'Loop playlist videos'"
|
||||
placement="bottom auto"
|
||||
container="body"
|
||||
></my-global-icon>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
|
|
@ -39,6 +39,10 @@
|
|||
display: flex;
|
||||
margin: 10px 0;
|
||||
|
||||
my-global-icon:not(:last-child) {
|
||||
margin-right: .5rem;
|
||||
}
|
||||
|
||||
my-global-icon {
|
||||
&:not(.active) {
|
||||
opacity: .5
|
||||
|
|
|
@ -3,11 +3,11 @@ import { VideoPlaylist } from '@app/shared/video-playlist/video-playlist.model'
|
|||
import { ComponentPagination } from '@app/shared/rest/component-pagination.model'
|
||||
import { VideoDetails, VideoPlaylistPrivacy } from '@shared/models'
|
||||
import { Router } from '@angular/router'
|
||||
import { User, UserService } from '@app/shared'
|
||||
import { UserService } from '@app/shared'
|
||||
import { AuthService, Notifier } from '@app/core'
|
||||
import { VideoPlaylistService } from '@app/shared/video-playlist/video-playlist.service'
|
||||
import { VideoPlaylistElement } from '@app/shared/video-playlist/video-playlist-element.model'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
||||
import { peertubeLocalStorage, peertubeSessionStorage } from '@app/shared/misc/peertube-web-storage'
|
||||
import { I18n } from '@ngx-translate/i18n-polyfill'
|
||||
|
||||
@Component({
|
||||
|
@ -17,6 +17,7 @@ import { I18n } from '@ngx-translate/i18n-polyfill'
|
|||
})
|
||||
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
|
||||
|
@ -30,6 +31,8 @@ export class VideoWatchPlaylistComponent {
|
|||
|
||||
autoPlayNextVideoPlaylist: boolean
|
||||
autoPlayNextVideoPlaylistSwitchText = ''
|
||||
loopPlaylist: boolean
|
||||
loopPlaylistSwitchText = ''
|
||||
noPlaylistVideos = false
|
||||
currentPlaylistPosition = 1
|
||||
|
||||
|
@ -45,6 +48,9 @@ export class VideoWatchPlaylistComponent {
|
|||
? this.auth.getUser().autoPlayNextVideoPlaylist
|
||||
: peertubeLocalStorage.getItem(VideoWatchPlaylistComponent.LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST) !== 'false'
|
||||
this.setAutoPlayNextVideoPlaylistSwitchText()
|
||||
|
||||
this.loopPlaylist = peertubeSessionStorage.getItem(VideoWatchPlaylistComponent.SESSION_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST) === 'true'
|
||||
this.setLoopPlaylistSwitchText()
|
||||
}
|
||||
|
||||
onPlaylistVideosNearOfBottom () {
|
||||
|
@ -121,9 +127,9 @@ export class VideoWatchPlaylistComponent {
|
|||
this.onPlaylistVideosNearOfBottom()
|
||||
}
|
||||
|
||||
navigateToNextPlaylistVideo () {
|
||||
navigateToNextPlaylistVideo (_next: VideoPlaylistElement = null) {
|
||||
if (this.currentPlaylistPosition < this.playlistPagination.totalItems) {
|
||||
const next = this.playlistElements.find(e => e.position === this.currentPlaylistPosition + 1)
|
||||
const next = _next || this.playlistElements.find(e => e.position === this.currentPlaylistPosition + 1)
|
||||
|
||||
if (!next || !next.video) {
|
||||
this.currentPlaylistPosition++
|
||||
|
@ -134,6 +140,9 @@ export class VideoWatchPlaylistComponent {
|
|||
const start = next.startTimestamp
|
||||
const stop = next.stopTimestamp
|
||||
this.router.navigate([],{ queryParams: { videoId: next.video.uuid, start, stop } })
|
||||
} else if (this.loopPlaylist) {
|
||||
this.currentPlaylistPosition = 0
|
||||
this.navigateToNextPlaylistVideo(this.playlistElements.find(e => e.position === this.currentPlaylistPosition))
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -160,9 +169,25 @@ export class VideoWatchPlaylistComponent {
|
|||
}
|
||||
}
|
||||
|
||||
switchLoopPlaylist () {
|
||||
this.loopPlaylist = !this.loopPlaylist
|
||||
this.setLoopPlaylistSwitchText()
|
||||
|
||||
peertubeSessionStorage.setItem(
|
||||
VideoWatchPlaylistComponent.SESSION_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST,
|
||||
this.loopPlaylist.toString()
|
||||
)
|
||||
}
|
||||
|
||||
private setAutoPlayNextVideoPlaylistSwitchText () {
|
||||
this.autoPlayNextVideoPlaylistSwitchText = this.i18n('{{verb}} autoplay for playlists', {
|
||||
verb: this.autoPlayNextVideoPlaylist ? this.i18n('Disable') : this.i18n('Enable')
|
||||
})
|
||||
this.autoPlayNextVideoPlaylistSwitchText = this.autoPlayNextVideoPlaylist
|
||||
? this.i18n('Stop autoplaying next video')
|
||||
: this.i18n('Autoplay next video')
|
||||
}
|
||||
|
||||
private setLoopPlaylistSwitchText () {
|
||||
this.loopPlaylistSwitchText = this.loopPlaylist
|
||||
? this.i18n('Stop looping playlist videos')
|
||||
: this.i18n('Loop playlist videos')
|
||||
}
|
||||
}
|
||||
|
|
|
@ -2,7 +2,7 @@ import { catchError } from 'rxjs/operators'
|
|||
import { ChangeDetectorRef, Component, ElementRef, Inject, LOCALE_ID, NgZone, OnDestroy, OnInit, ViewChild } from '@angular/core'
|
||||
import { ActivatedRoute, Router } from '@angular/router'
|
||||
import { RedirectService } from '@app/core/routing/redirect.service'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
||||
import { peertubeLocalStorage, peertubeSessionStorage } from '@app/shared/misc/peertube-web-storage'
|
||||
import { VideoSupportComponent } from '@app/videos/+video-watch/modal/video-support.component'
|
||||
import { MetaService } from '@ngx-meta/core'
|
||||
import { AuthUser, Notifier, ServerService } from '@app/core'
|
||||
|
@ -46,7 +46,6 @@ import { RecommendedVideosComponent } from '../recommendations/recommended-video
|
|||
})
|
||||
export class VideoWatchComponent implements OnInit, OnDestroy {
|
||||
private static LOCAL_STORAGE_PRIVACY_CONCERN_KEY = 'video-watch-privacy-concern'
|
||||
private static LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO = 'auto_play_next_video'
|
||||
|
||||
@ViewChild('videoWatchPlaylist', { static: true }) videoWatchPlaylist: VideoWatchPlaylistComponent
|
||||
@ViewChild('videoShareModal', { static: false }) videoShareModal: VideoShareComponent
|
||||
|
@ -439,11 +438,11 @@ export class VideoWatchComponent implements OnInit, OnDestroy {
|
|||
if (this.playlist) {
|
||||
if (
|
||||
this.user && this.user.autoPlayNextVideoPlaylist ||
|
||||
peertubeLocalStorage.getItem(VideoWatchPlaylistComponent.LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST) === 'true'
|
||||
peertubeSessionStorage.getItem(VideoWatchPlaylistComponent.SESSION_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST) === 'true'
|
||||
) this.zone.run(() => this.videoWatchPlaylist.navigateToNextPlaylistVideo())
|
||||
} else if (
|
||||
this.user && this.user.autoPlayNextVideo ||
|
||||
peertubeLocalStorage.getItem(RecommendedVideosComponent.LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO) === 'true'
|
||||
peertubeSessionStorage.getItem(RecommendedVideosComponent.SESSION_STORAGE_AUTO_PLAY_NEXT_VIDEO) === 'true'
|
||||
) {
|
||||
this.zone.run(() => this.autoplayNext())
|
||||
}
|
||||
|
@ -453,7 +452,7 @@ export class VideoWatchComponent implements OnInit, OnDestroy {
|
|||
if (this.playlist) {
|
||||
if (
|
||||
this.user && this.user.autoPlayNextVideoPlaylist ||
|
||||
peertubeLocalStorage.getItem(VideoWatchPlaylistComponent.LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST) === 'true'
|
||||
peertubeSessionStorage.getItem(VideoWatchPlaylistComponent.SESSION_STORAGE_AUTO_PLAY_NEXT_VIDEO_PLAYLIST) === 'true'
|
||||
) this.zone.run(() => this.videoWatchPlaylist.navigateToNextPlaylistVideo())
|
||||
}
|
||||
})
|
||||
|
|
|
@ -7,7 +7,7 @@ import { RecommendedVideosStore } from '@app/videos/recommendations/recommended-
|
|||
import { User } from '@app/shared'
|
||||
import { AuthService, Notifier } from '@app/core'
|
||||
import { UserService } from '@app/shared/users/user.service'
|
||||
import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
||||
import { peertubeSessionStorage } from '@app/shared/misc/peertube-web-storage'
|
||||
|
||||
@Component({
|
||||
selector: 'my-recommended-videos',
|
||||
|
@ -15,7 +15,7 @@ import { peertubeLocalStorage } from '@app/shared/misc/peertube-local-storage'
|
|||
styleUrls: [ './recommended-videos.component.scss' ]
|
||||
})
|
||||
export class RecommendedVideosComponent implements OnChanges {
|
||||
static LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO = 'auto_play_next_video'
|
||||
static SESSION_STORAGE_AUTO_PLAY_NEXT_VIDEO = 'auto_play_next_video'
|
||||
|
||||
@Input() inputRecommendation: RecommendationInfo
|
||||
@Input() user: User
|
||||
|
@ -39,7 +39,7 @@ export class RecommendedVideosComponent implements OnChanges {
|
|||
|
||||
this.autoPlayNextVideo = this.authService.isLoggedIn()
|
||||
? this.authService.getUser().autoPlayNextVideo
|
||||
: peertubeLocalStorage.getItem(RecommendedVideosComponent.LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO) === 'true' || false
|
||||
: peertubeSessionStorage.getItem(RecommendedVideosComponent.SESSION_STORAGE_AUTO_PLAY_NEXT_VIDEO) === 'true' || false
|
||||
}
|
||||
|
||||
public ngOnChanges (): void {
|
||||
|
@ -53,7 +53,7 @@ export class RecommendedVideosComponent implements OnChanges {
|
|||
}
|
||||
|
||||
switchAutoPlayNextVideo () {
|
||||
peertubeLocalStorage.setItem(RecommendedVideosComponent.LOCAL_STORAGE_AUTO_PLAY_NEXT_VIDEO, this.autoPlayNextVideo.toString())
|
||||
peertubeSessionStorage.setItem(RecommendedVideosComponent.SESSION_STORAGE_AUTO_PLAY_NEXT_VIDEO, this.autoPlayNextVideo.toString())
|
||||
|
||||
if (this.authService.isLoggedIn()) {
|
||||
const details = {
|
||||
|
|
|
@ -0,0 +1 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-repeat"><polyline points="17 1 21 5 17 9"></polyline><path d="M3 11V9a4 4 0 0 1 4-4h14"></path><polyline points="7 23 3 19 7 15"></polyline><path d="M21 13v2a4 4 0 0 1-4 4H3"></path></svg>
|
After Width: | Height: | Size: 392 B |
Loading…
Reference in New Issue