a simple web player for subsonic
tinysub.devins.page
subsonic
navidrome
javascript
1// app state with api, library, queue, and user preferences
2const state = {
3 api: null,
4 library: [],
5 playlists: [],
6 queue: [],
7 queueIndex: -1,
8 favorites: new Set(),
9 loop: false,
10 expanded: {
11 artists: false,
12 playlists: false,
13 items: {
14 artists: {},
15 albums: {},
16 },
17 },
18 settings: {
19 scrobbling: true,
20 dynamicFavicon: true,
21 artArtist: 0,
22 artAlbum: 32,
23 artSong: 0,
24 artNowPlaying: 128,
25 },
26};
27
28// dom element references cached for quick access
29const ui = {
30 loginForm: document.getElementById(DOM_IDS.LOGIN_FORM),
31 serverInput: document.getElementById(DOM_IDS.SERVER_INPUT),
32 usernameInput: document.getElementById(DOM_IDS.USERNAME_INPUT),
33 passwordInput: document.getElementById(DOM_IDS.PASSWORD_INPUT),
34 authError: document.getElementById(DOM_IDS.AUTH_ERROR),
35 artistsTree: document.getElementById(DOM_IDS.LIBRARY_TREE),
36 playlistsTree: document.getElementById(DOM_IDS.PLAYLISTS_TREE),
37 queueList: document.getElementById(DOM_IDS.QUEUE_LIST),
38 queueCount: document.getElementById(DOM_IDS.QUEUE_COUNT),
39 coverArt: document.getElementById(DOM_IDS.COVER_ART),
40 trackTitle: document.getElementById(DOM_IDS.TRACK_TITLE),
41 trackArtist: document.getElementById(DOM_IDS.TRACK_ARTIST),
42 trackLyric: document.getElementById(DOM_IDS.TRACK_LYRIC),
43 player: document.getElementById(DOM_IDS.PLAYER),
44 playBtn: document.getElementById(DOM_IDS.PLAY_BTN),
45 prevBtn: document.getElementById(DOM_IDS.PREV_BTN),
46 nextBtn: document.getElementById(DOM_IDS.NEXT_BTN),
47 progress: document.getElementById(DOM_IDS.PROGRESS),
48 timeDisplay: document.getElementById(DOM_IDS.TIME_DISPLAY),
49 settingsBtn: document.getElementById("settings-btn"),
50 sectionToggles: document.querySelectorAll(`.${DOM_IDS.SECTION_TOGGLE}`),
51 loopBtn: document.getElementById(DOM_IDS.LOOP_BTN),
52 sortBtn: document.getElementById(DOM_IDS.SORT_BTN),
53 clearBtn: document.getElementById(DOM_IDS.CLEAR_BTN),
54};