zaphyra's git: domsonic

subsonic web-client

1 
2 
3 
4 
5 
6 
7 
8 
9 
10 
11 
12 
13 
14 
15 
16 
17 
18 
19 
20 
21 
22 
23 
24 
25 
26 
27 
28 
29 
30 
31 
32 
33 
34 
35 
36 
37 
38 
39 
40 
41 
42 
43 
44 
45 
46 
47 
48 
49 
50 
51 
52 
53 
54 
55 
56 
57 
58 
59 
60 
61 
62 
63 
64 
65 
66 
67 
68 
69 
70 
71 
72 
73 
74 
75 
76 
77 
78 
79 
80 
81 
82 
83 
84 
85 
86 
87 
88 
89 
90 
91 
92 
93 
94 
95 
96 
97 
98 
99 
100 
101 
102 
103 
104 
105 
106 
107 
import { ref, watch } from 'vue'
import { orderBy } from 'lodash-es'

import type { Playlist } from '../types'

import { useMainStore } from '../store/main'
import { usePlaylistStore } from '../store/playlist'

import { EditPlaylistModal } from '../components/EditPlaylistModal.vine'
import { PlaylistList } from '../components/PlaylistList.vine'
import { 
  type ConfirmDialogExpose,
  ConfirmDialog
} from '../components/ConfirmDialog.vine'

export const PlaylistsView = () => {
  const
    mainStore = useMainStore(),
    playlistStore = usePlaylistStore(),

    showAddModal = ref(false),
    editingPlaylist = ref<Playlist | null>(null),
    confirmDialog = ref<ConfirmDialogExpose | null>(null),

    playlists = ref<Playlist[]>([]),

    closeModal = () => {
      editingPlaylist.value = null
      showAddModal.value = false
    },
    startCreate = () => {
      editingPlaylist.value = null
      showAddModal.value = true
    },
    openEditPlaylist = (playlist: Playlist) => {
      editingPlaylist.value = playlist
      showAddModal.value = true
    },

    createPlaylist = async (name: string) => {
      await playlistStore.create(name)
      closeModal()
    },
    updatePlaylist = async (playlist: Playlist) => {
      await playlistStore.update(playlist)
      closeModal()
    },
    deletePlaylist = async (id: string) => {
      if (!confirmDialog.value)
        return

      const userConfirmed = await confirmDialog.value.open(
        'Remove Playlist',
        'Do you really want to remove the playlist?'
      )

      if (!userConfirmed)
        return

      await playlistStore.delete(id)
    }

  watch(
    playlistStore,
    async () => {
      mainStore.isLoading = true
      playlists.value = playlistStore.playlists
      mainStore.isLoading = false
    },
    { deep: true, immediate: true }
  )

  return vine`
    <div class="row align-items-center justify-content-space-between">
      <span class="main-title">
        <Icon icon="playlist" />
        Playlists
      </span>
      <button variant="link" class="mx-2" @click="startCreate">
        <Icon icon="plus" />
        Create Playlist
      </button>
    </div>

    <PlaylistList
      v-if="playlists.length"
      :items="playlists"
      :is-playlist-view="true"
      @edit-playlist="openEditPlaylist"
      @remove-playlist="deletePlaylist"
    />

    <EmptyIndicator  v-if="!mainStore.isLoading && playlists.length === 0" />

    <Teleport to="#dialogBoxes">
      <ConfirmDialog ref="confirmDialog" />
      <EditPlaylistModal
        v-if="showAddModal"
        :playlist="editingPlaylist"
        :mode="editingPlaylist ? 'edit' : 'create'"
        @create-playlist="createPlaylist"
        @update-playlist="updatePlaylist"
        @close="closeModal"
      />
    </Teleport>
  `
}