Skip to content

Commit ab81c7d

Browse files
Fix deleted videos appears when another video added to another playlist (FreeTubeApp#7681)
* $ Rename local data, extra timeout value * ! Fix deleted videos appears when another video added to another playlist
1 parent 24a344a commit ab81c7d

File tree

2 files changed

+61
-38
lines changed

2 files changed

+61
-38
lines changed

src/renderer/views/Playlist/Playlist.js

Lines changed: 48 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,7 @@ export default defineComponent({
8181
videoSearchQuery: '',
8282

8383
promptOpen: false,
84-
deletedPlaylistItemIds: [],
84+
toBeDeletedPlaylistItemIds: [],
8585
// Present = shown
8686
undoToastAbortController: null,
8787
}
@@ -193,7 +193,7 @@ export default defineComponent({
193193
const playlistItems = this.getPlaylistItemsWithDuration()
194194
return getSortedPlaylistItems(playlistItems, this.sortOrder, this.currentLocale)
195195
}
196-
return getSortedPlaylistItems(this.playlistItems, this.sortOrder, this.currentLocale)
196+
return getSortedPlaylistItems(this.shownPlaylistItems, this.sortOrder, this.currentLocale)
197197
},
198198
visiblePlaylistItems: function () {
199199
if (!this.isUserPlaylistRequested) {
@@ -244,6 +244,35 @@ export default defineComponent({
244244
sortBySelectValues() {
245245
return this.sortByValues
246246
},
247+
totalPlaylistDuration() {
248+
const totalSeconds = this.shownPlaylistItems.reduce((acc, video) => {
249+
if (typeof video.lengthSeconds !== 'number') {
250+
return NaN
251+
}
252+
return acc + video.lengthSeconds
253+
}, 0)
254+
return totalSeconds
255+
},
256+
noPlaylistItemsPendingDeletion() {
257+
return this.toBeDeletedPlaylistItemIds.length === 0
258+
},
259+
shownPlaylistItems() {
260+
if (this.noPlaylistItemsPendingDeletion) {
261+
return this.playlistItems
262+
}
263+
264+
return this.playlistItems.filter((v) => !this.toBeDeletedPlaylistItemIds.includes(v.playlistItemId))
265+
},
266+
shownPlaylistItemCount() {
267+
return this.shownPlaylistItems.length
268+
},
269+
shownVideoCount() {
270+
if (this.isUserPlaylistRequested) {
271+
return this.shownPlaylistItemCount
272+
}
273+
274+
return this.videoCount
275+
},
247276
},
248277
watch: {
249278
$route() {
@@ -264,14 +293,16 @@ export default defineComponent({
264293
// Re-fetch from local store when current user playlist updated
265294
this.getPlaylistInfoDebounce()
266295
},
267-
selectedUserPlaylistVideoCount() {
296+
async selectedUserPlaylistVideoCount() {
268297
// Monitoring `selectedUserPlaylistVideos` makes this function called
269298
// Even when the same array object is returned
270299
// So length is monitored instead
271300
// Assuming in user playlist video cannot be swapped without length change
272301

273302
// Re-fetch from local store when current user playlist videos updated
274-
this.getPlaylistInfoDebounce()
303+
// MUST NOT use `getPlaylistInfoDebounce` as it will cause delay in data update
304+
// Causing deleted videos to reappear for one frame
305+
this.getPlaylistInfo()
275306
},
276307
},
277308
created: function () {
@@ -424,7 +455,6 @@ export default defineComponent({
424455
this.firstVideoPlaylistItemId = ''
425456
}
426457
this.viewCount = 0
427-
this.videoCount = playlist.videos.length
428458
const dateString = new Date(playlist.lastUpdatedAt)
429459
this.lastUpdated = dateString.toLocaleDateString(this.currentLocale, { year: 'numeric', month: 'short', day: 'numeric' })
430460
this.channelName = ''
@@ -444,7 +474,7 @@ export default defineComponent({
444474
},
445475

446476
getPlaylistItemsWithDuration() {
447-
const modifiedPlaylistItems = deepCopy(this.playlistItems)
477+
const modifiedPlaylistItems = deepCopy(this.shownPlaylistItems)
448478
let anyVideoMissingDuration = false
449479
modifiedPlaylistItems.forEach(video => {
450480
if (videoDurationPresent(video)) { return }
@@ -482,10 +512,10 @@ export default defineComponent({
482512
this.isLoadingMore = true
483513

484514
nextTick(() => {
485-
if (this.userPlaylistVisibleLimit + 100 < this.videoCount) {
515+
if (this.userPlaylistVisibleLimit + 100 < this.shownVideoCount) {
486516
this.userPlaylistVisibleLimit += 100
487517
} else {
488-
this.userPlaylistVisibleLimit = this.videoCount
518+
this.userPlaylistVisibleLimit = this.shownVideoCount
489519
}
490520

491521
this.isLoadingMore = false
@@ -590,33 +620,26 @@ export default defineComponent({
590620

591621
removeVideoFromPlaylist: function (videoId, playlistItemId) {
592622
try {
593-
const playlistItems = [].concat(this.playlistItems)
594-
const tempPlaylistItems = [].concat(this.playlistItems)
595-
596623
const videoIndex = this.playlistItems.findIndex((video) => {
597624
return video.videoId === videoId && video.playlistItemId === playlistItemId
598625
})
599626

600627
if (videoIndex !== -1) {
601-
this.deletedPlaylistItemIds.push(this.playlistItems[videoIndex].playlistItemId)
602-
playlistItems.splice(videoIndex, 1)
603-
this.playlistItems = playlistItems
604-
this.videoCount = playlistItems.length
628+
this.toBeDeletedPlaylistItemIds.push(this.playlistItems[videoIndex].playlistItemId)
605629

606630
// Only show toast when no existing toast shown
607631
if (this.undoToastAbortController == null) {
608632
this.undoToastAbortController = new AbortController()
633+
const timeoutMs = 5 * 1000
609634
const actualRemoveVideosTimeout = setTimeout(() => {
610635
this.removeToBeDeletedVideosSometimes()
611-
}, 5000)
636+
}, timeoutMs)
612637
showToast(
613638
this.$t('User Playlists.SinglePlaylistView.Toast["Video has been removed. Click here to undo."]'),
614-
5000,
639+
timeoutMs,
615640
() => {
616-
this.playlistItems = tempPlaylistItems
617-
this.videoCount = tempPlaylistItems.length
618641
clearTimeout(actualRemoveVideosTimeout)
619-
this.deletedPlaylistItemIds = []
642+
this.toBeDeletedPlaylistItemIds = []
620643
this.undoToastAbortController = null
621644
},
622645
this.undoToastAbortController.signal,
@@ -629,15 +652,15 @@ export default defineComponent({
629652
}
630653
},
631654

632-
removeToBeDeletedVideosSometimes() {
655+
async removeToBeDeletedVideosSometimes() {
633656
if (this.isLoading) { return }
634657

635-
if (this.deletedPlaylistItemIds.length > 0) {
636-
this.removeVideos({
658+
if (this.toBeDeletedPlaylistItemIds.length > 0) {
659+
await this.removeVideos({
637660
_id: this.playlistId,
638-
playlistItemIds: this.deletedPlaylistItemIds,
661+
playlistItemIds: this.toBeDeletedPlaylistItemIds,
639662
})
640-
this.deletedPlaylistItemIds = []
663+
this.toBeDeletedPlaylistItemIds = []
641664
this.undoToastAbortController?.abort()
642665
this.undoToastAbortController = null
643666
}

src/renderer/views/Playlist/Playlist.vue

Lines changed: 13 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
<template>
22
<div
3-
:class="{ [listType]: true, playlistInEditMode, hasNoPlaylistDescription: !playlistDescription, oneOrFewer: videoCount < 2 }"
3+
:class="{ [listType]: true, playlistInEditMode, hasNoPlaylistDescription: !playlistDescription, oneOrFewer: shownVideoCount < 2 }"
44
class="playlistPage"
55
>
66
<ft-loader
@@ -25,12 +25,12 @@
2525
:channel-id="channelId"
2626
:last-updated="lastUpdated"
2727
:description="playlistDescription"
28-
:video-count="videoCount"
29-
:videos="playlistItems"
28+
:video-count="shownVideoCount"
29+
:videos="shownPlaylistItems"
3030
:view-count="viewCount"
3131
:info-source="infoSource"
3232
:more-video-data-available="moreVideoDataAvailable"
33-
:search-video-mode-allowed="isUserPlaylistRequested && videoCount > 1"
33+
:search-video-mode-allowed="isUserPlaylistRequested && shownVideoCount > 1"
3434
:search-video-mode-enabled="playlistInVideoSearchMode"
3535
:search-query-text="searchQueryTextRequested"
3636
:theme="listType === 'list' ? 'base' : 'top-bar'"
@@ -48,10 +48,10 @@
4848
class="playlistItemsCard"
4949
>
5050
<template
51-
v-if="playlistItems.length > 0"
51+
v-if="shownPlaylistItems.length > 0"
5252
>
5353
<ft-select
54-
v-if="isUserPlaylistRequested && playlistItems.length > 1"
54+
v-if="isUserPlaylistRequested && shownPlaylistItems.length > 1"
5555
class="sortSelect"
5656
:value="sortOrder"
5757
:select-names="sortBySelectNames"
@@ -74,9 +74,9 @@
7474
:hide-forbidden-titles="false"
7575
:always-show-add-to-playlist-button="true"
7676
:quick-bookmark-button-enabled="quickBookmarkButtonEnabled"
77-
:can-move-video-up="!playlistInVideoSearchMode && isSortOrderCustom"
78-
:can-move-video-down="!playlistInVideoSearchMode && isSortOrderCustom"
79-
:playlist-items-length="playlistItems.length"
77+
:can-move-video-up="!playlistInVideoSearchMode && isSortOrderCustom && noPlaylistItemsPendingDeletion"
78+
:can-move-video-down="!playlistInVideoSearchMode && isSortOrderCustom && noPlaylistItemsPendingDeletion"
79+
:playlist-items-length="shownPlaylistItems.length"
8080
:can-remove-from-playlist="true"
8181
@move-video-up="moveVideoUp"
8282
@move-video-down="moveVideoDown"
@@ -95,15 +95,15 @@
9595
:data="item"
9696
:playlist-id="playlistId"
9797
:playlist-type="infoSource"
98-
:playlist-index="playlistInVideoSearchMode ? playlistItems.findIndex(i => i === item) : index"
98+
:playlist-index="playlistInVideoSearchMode ? shownPlaylistItems.findIndex(i => i === item) : index"
9999
:playlist-item-id="item.playlistItemId"
100100
appearance="result"
101101
:always-show-add-to-playlist-button="true"
102102
:quick-bookmark-button-enabled="quickBookmarkButtonEnabled"
103-
:can-move-video-up="index > 0 && !playlistInVideoSearchMode && isSortOrderCustom"
104-
:can-move-video-down="index < playlistItems.length - 1 && !playlistInVideoSearchMode && isSortOrderCustom"
103+
:can-move-video-up="index > 0 && !playlistInVideoSearchMode && isSortOrderCustom && noPlaylistItemsPendingDeletion"
104+
:can-move-video-down="index < shownPlaylistItems.length - 1 && !playlistInVideoSearchMode && isSortOrderCustom && noPlaylistItemsPendingDeletion"
105105
:can-remove-from-playlist="true"
106-
:video-index="playlistInVideoSearchMode ? playlistItems.findIndex(i => i === item) : index"
106+
:video-index="playlistInVideoSearchMode ? shownPlaylistItems.findIndex(i => i === item) : index"
107107
:initial-visible-state="index < 10"
108108
@move-video-up="moveVideoUp(item.videoId, item.playlistItemId)"
109109
@move-video-down="moveVideoDown(item.videoId, item.playlistItemId)"

0 commit comments

Comments
 (0)