@christianriedl/media 1.0.304 → 1.0.306
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/iMedia.d.ts
CHANGED
|
@@ -367,6 +367,7 @@ export interface IPlaylistService {
|
|
|
367
367
|
soundbarVolume: number;
|
|
368
368
|
searchFeeds(query: Dictionary<any>, limit?: number): Promise<IRssFeed[]>;
|
|
369
369
|
getFeed(rssUrl: string): Promise<IRssFeed | null>;
|
|
370
|
+
getCategories(owner: string): Promise<string[]>;
|
|
370
371
|
play(url: string): Promise<boolean>;
|
|
371
372
|
playList(urls: string[], clear: boolean, index?: number): Promise<boolean>;
|
|
372
373
|
playCommand(cmd: EPlaylistCommand): Promise<boolean>;
|
|
@@ -9,9 +9,11 @@ export declare class PlaylistService implements IPlaylistService {
|
|
|
9
9
|
soundbarVolume: number;
|
|
10
10
|
setSoundbar: (name: string, value: string) => Promise<boolean>;
|
|
11
11
|
getSoundbarValue: (name: string) => any;
|
|
12
|
+
cachedCategories: Dictionary<string[]>;
|
|
12
13
|
constructor(rest: IRest, log: ILogger, getSoundbarValue: (name: string) => any, setSoundbar: (name: string, value: string) => Promise<boolean>);
|
|
13
14
|
searchFeeds(query: Dictionary<any>, limit?: number): Promise<IRssFeed[]>;
|
|
14
15
|
getFeed(rssUrl: string): Promise<IRssFeed | null>;
|
|
16
|
+
getCategories(owner: string): Promise<string[]>;
|
|
15
17
|
play(url: string): Promise<boolean>;
|
|
16
18
|
playList(urls: string[], clear: boolean, index?: number): Promise<boolean>;
|
|
17
19
|
playCommand(cmd: EPlaylistCommand): Promise<boolean>;
|
package/dist/playlistService.js
CHANGED
|
@@ -8,6 +8,7 @@ export class PlaylistService {
|
|
|
8
8
|
soundbarVolume;
|
|
9
9
|
setSoundbar;
|
|
10
10
|
getSoundbarValue;
|
|
11
|
+
cachedCategories;
|
|
11
12
|
constructor(rest, log, getSoundbarValue, setSoundbar) {
|
|
12
13
|
this.log = log;
|
|
13
14
|
this.rest = rest;
|
|
@@ -15,6 +16,8 @@ export class PlaylistService {
|
|
|
15
16
|
this.getSoundbarValue = getSoundbarValue;
|
|
16
17
|
this.setSoundbar = setSoundbar;
|
|
17
18
|
this.soundbarOn = false;
|
|
19
|
+
this.cachedCategories = {};
|
|
20
|
+
;
|
|
18
21
|
}
|
|
19
22
|
async searchFeeds(query, limit) {
|
|
20
23
|
query['limit'] = limit ?? 50;
|
|
@@ -25,6 +28,20 @@ export class PlaylistService {
|
|
|
25
28
|
const res = await this.rest.getData('apiplaylist/feed', { rssUrl: rssUrl });
|
|
26
29
|
return res.ok ? res.result : null;
|
|
27
30
|
}
|
|
31
|
+
async getCategories(owner) {
|
|
32
|
+
let categories = this.cachedCategories[owner];
|
|
33
|
+
if (!categories) {
|
|
34
|
+
const res = await this.rest.getData('apiplaylist/feed/categories', { owner: owner });
|
|
35
|
+
if (!res.ok || !res.result) {
|
|
36
|
+
return [''];
|
|
37
|
+
}
|
|
38
|
+
categories = [''];
|
|
39
|
+
categories.push(...res.result);
|
|
40
|
+
this.cachedCategories[owner] = categories;
|
|
41
|
+
;
|
|
42
|
+
}
|
|
43
|
+
return categories;
|
|
44
|
+
}
|
|
28
45
|
/*
|
|
29
46
|
async getTitles(): Promise<string[]> {
|
|
30
47
|
const res = await this.rest.getData<string[]>('apiplaylist/title');
|
|
@@ -65,6 +82,8 @@ export class PlaylistService {
|
|
|
65
82
|
return res.ok ? res.result : false;
|
|
66
83
|
}
|
|
67
84
|
async playCommand(cmd) {
|
|
85
|
+
if (cmd == EPlaylistCommand.Stop && this.getSoundbarValue('On') === false)
|
|
86
|
+
return true;
|
|
68
87
|
this.soundbarOn = await this.ensureSoundbarOn();
|
|
69
88
|
if (!this.soundbarOn)
|
|
70
89
|
return false;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"playlistService.js","sourceRoot":"","sources":["../src/playlistService.ts"],"names":[],"mappings":"AACA,OAAO,EAAW,MAAM,EAAc,MAAM,uBAAuB,CAAC;AACpE,OAAO,EAAY,gBAAgB,EAAoC,MAAM,UAAU,CAAC;AAExF,MAAM,OAAO,eAAe;IACxB,IAAI,CAAQ;IACZ,QAAQ,CAAS;IACjB,GAAG,CAAU;IACb,UAAU,CAAU;IACpB,cAAc,CAAS;IACvB,WAAW,CAAoD;IAC/D,gBAAgB,CAAwB;IACxC,YAAY,IAAW,EAAE,GAAY,EAAE,gBAAuC,EAAE,WAA8D;QAC1I,IAAI,CAAC,GAAG,GAAG,GAAG,CAAC;QACf,IAAI,CAAC,IAAI,GAAG,IAAI,CAAC;QACjB,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC,UAAU,CAAC;QAChC,IAAI,CAAC,gBAAgB,GAAG,gBAAgB,CAAC;QACzC,IAAI,CAAC,WAAW,GAAG,WAAW,CAAC;QACtC,IAAI,CAAC,UAAU,GAAG,KAAK,CAAC;
|
|
1
|
+
{"version":3,"file":"playlistService.js","sourceRoot":"","sources":["../src/playlistService.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -6,6 +6,7 @@
|
|
|
6
6
|
import { getPlaylistSymbol, IPlaylistService, IPlaylistState, IRssFeed, IRssItem, EPlaylistCommand, EFeedType } from '@christianriedl/media';
|
|
7
7
|
|
|
8
8
|
const appState = inject(appStateSymbol)!;
|
|
9
|
+
const appConfig = inject(appConfigSymbol)!;
|
|
9
10
|
const getPlaylistService = inject(getPlaylistSymbol)!;
|
|
10
11
|
const playlistService = getPlaylistService() ;
|
|
11
12
|
const heightStyle = computed<StyleValue>(() => { return { height: appState.bodyHeight.value + 'px', overflowY: 'auto' } });
|
|
@@ -22,6 +23,7 @@
|
|
|
22
23
|
const listHeight = ref(0);
|
|
23
24
|
const playerNames = ['Local', 'Soundbar'];
|
|
24
25
|
const currentPlayer = ref<string>(playerNames[0]);
|
|
26
|
+
const orf = ref(true);
|
|
25
27
|
const playLocal = computed(() => currentPlayer.value == 'Local');
|
|
26
28
|
const playIndex = ref(-1);
|
|
27
29
|
const itemIndex = ref(0);
|
|
@@ -43,21 +45,25 @@
|
|
|
43
45
|
});
|
|
44
46
|
|
|
45
47
|
const feedTypes = Helper.getEnumOptions(EFeedType);
|
|
46
|
-
const feedType = ref<EFeedType>(
|
|
48
|
+
const feedType = ref<EFeedType>(EFeedType.Podcast);
|
|
47
49
|
const countries = ["", "AT", "DE", "US"];
|
|
48
50
|
const country = ref("");
|
|
49
51
|
const query = ref("");
|
|
52
|
+
const categories = ref<string[]>([]);
|
|
53
|
+
const category = ref("");
|
|
54
|
+
|
|
50
55
|
const limit = ref(50);
|
|
51
56
|
|
|
52
57
|
onMounted(async () => {
|
|
58
|
+
statusTimer = 0;
|
|
53
59
|
playlistService.log.info('OnlinePodcastsPage created');
|
|
54
60
|
await start();
|
|
55
61
|
});
|
|
56
62
|
onUnmounted(() => {
|
|
57
63
|
if (statusTimer > 0) {
|
|
58
64
|
window.clearTimeout(statusTimer);
|
|
59
|
-
statusTimer = 0;
|
|
60
65
|
}
|
|
66
|
+
statusTimer = -1;
|
|
61
67
|
});
|
|
62
68
|
async function start() {
|
|
63
69
|
if (route.query?.rssUrl) {
|
|
@@ -70,6 +76,9 @@
|
|
|
70
76
|
}
|
|
71
77
|
}
|
|
72
78
|
else {
|
|
79
|
+
if (categories.value.length == 0) {
|
|
80
|
+
categories.value = await playlistService.getCategories('ORF');
|
|
81
|
+
}
|
|
73
82
|
search.value = true;
|
|
74
83
|
}
|
|
75
84
|
computeListHeight();
|
|
@@ -88,10 +97,17 @@
|
|
|
88
97
|
}
|
|
89
98
|
async function onSearch() {
|
|
90
99
|
const dict: Dictionary<any> = {};
|
|
91
|
-
if (
|
|
92
|
-
dict[
|
|
93
|
-
|
|
94
|
-
|
|
100
|
+
if (orf.value) {
|
|
101
|
+
dict['owner'] = 'ORF';
|
|
102
|
+
if (category.value)
|
|
103
|
+
dict['category'] = category.value;
|
|
104
|
+
}
|
|
105
|
+
else {
|
|
106
|
+
if (feedType.value != EFeedType.Unknown)
|
|
107
|
+
dict["media"] = EFeedType[feedType.value];
|
|
108
|
+
if (country.value != "")
|
|
109
|
+
dict["country"] = country.value;;
|
|
110
|
+
}
|
|
95
111
|
dict["query"] = query.value;
|
|
96
112
|
const fds = await playlistService.searchFeeds(dict, limit.value);
|
|
97
113
|
feeds.splice (0, feeds.length, ...fds);
|
|
@@ -124,6 +140,16 @@
|
|
|
124
140
|
play();
|
|
125
141
|
computeListHeight();
|
|
126
142
|
}
|
|
143
|
+
|
|
144
|
+
function download(item: IRssItem) {
|
|
145
|
+
const anchor = document.createElement("a");
|
|
146
|
+
anchor.href = item.link;
|
|
147
|
+
anchor.download = item.title + ".mp3";
|
|
148
|
+
document.body.appendChild(anchor);
|
|
149
|
+
anchor.click();
|
|
150
|
+
document.body.removeChild(anchor);
|
|
151
|
+
}
|
|
152
|
+
|
|
127
153
|
function listBack() {
|
|
128
154
|
router.back();
|
|
129
155
|
}
|
|
@@ -136,7 +162,8 @@
|
|
|
136
162
|
volumeCount--;
|
|
137
163
|
else
|
|
138
164
|
volume.value = playlistService.soundbarVolume;
|
|
139
|
-
|
|
165
|
+
if (statusTimer >= 0)
|
|
166
|
+
statusTimer = window.setTimeout(async () => getStatus(), 1000);
|
|
140
167
|
}
|
|
141
168
|
|
|
142
169
|
function toSubTitle(f: IRssFeed): string {
|
|
@@ -168,6 +195,15 @@
|
|
|
168
195
|
}
|
|
169
196
|
return r;
|
|
170
197
|
}
|
|
198
|
+
|
|
199
|
+
function firstGenre(s?: string) {
|
|
200
|
+
if (!s)
|
|
201
|
+
return "";
|
|
202
|
+
const idx = s.indexOf('|');
|
|
203
|
+
if (idx > 0)
|
|
204
|
+
return s.substring(0, idx);
|
|
205
|
+
return s;
|
|
206
|
+
}
|
|
171
207
|
function onEnded() {
|
|
172
208
|
}
|
|
173
209
|
function onTimeUpdate() {
|
|
@@ -222,8 +258,20 @@
|
|
|
222
258
|
selectedItem.value = items[playIndex.value + 1];
|
|
223
259
|
play();
|
|
224
260
|
}
|
|
261
|
+
async function stopAll() {
|
|
262
|
+
if (audio.value) {
|
|
263
|
+
audio.value!.pause();
|
|
264
|
+
audio.value!.currentTime = 0;
|
|
265
|
+
}
|
|
266
|
+
await playlistService.playCommand(EPlaylistCommand.Stop);
|
|
267
|
+
}
|
|
225
268
|
async function stop() {
|
|
226
|
-
|
|
269
|
+
if (playLocal.value) {
|
|
270
|
+
audio.value!.pause();
|
|
271
|
+
audio.value!.currentTime = 0;
|
|
272
|
+
}
|
|
273
|
+
else
|
|
274
|
+
await playlistService.playCommand(EPlaylistCommand.Stop);
|
|
227
275
|
}
|
|
228
276
|
async function changeVolume() {
|
|
229
277
|
if (volumeTimer)
|
|
@@ -243,74 +291,91 @@
|
|
|
243
291
|
<audio ref="audio" preload="none" @ended="onEnded" @timeupdate="onTimeUpdate">
|
|
244
292
|
</audio>
|
|
245
293
|
<v-container v-if="search" fluid>
|
|
246
|
-
<v-row class="align-center">
|
|
247
|
-
<v-col cols="1"
|
|
248
|
-
<v-col cols="
|
|
249
|
-
<
|
|
250
|
-
|
|
251
|
-
|
|
294
|
+
<v-row class="align-center" density="compact">
|
|
295
|
+
<v-col cols="1">Orf</v-col>
|
|
296
|
+
<v-col v-if="orf" cols="3">Category</v-col>
|
|
297
|
+
<template v-else>
|
|
298
|
+
<v-col cols="2">Type</v-col>
|
|
299
|
+
<v-col cols="1">Country</v-col>
|
|
300
|
+
</template>
|
|
301
|
+
<v-col cols="4">Query</v-col>
|
|
302
|
+
<v-col cols="2">Limit</v-col>
|
|
252
303
|
</v-row>
|
|
253
|
-
<v-row class="align-center">
|
|
304
|
+
<v-row class="align-center" density="compact">
|
|
254
305
|
<v-col cols="1">
|
|
306
|
+
<v-checkbox v-model="orf" hide-details density="compact"></v-checkbox>
|
|
255
307
|
</v-col>
|
|
256
|
-
<v-col cols="
|
|
257
|
-
<v-select density="compact" v-model="
|
|
258
|
-
:items="
|
|
308
|
+
<v-col v-if="orf" cols="3">
|
|
309
|
+
<v-select density="compact" v-model="category"
|
|
310
|
+
:items="categories"
|
|
259
311
|
persistent-hint hide-details single-line>
|
|
260
312
|
</v-select>
|
|
261
313
|
</v-col>
|
|
262
|
-
<v-
|
|
263
|
-
<v-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
314
|
+
<template v-else>
|
|
315
|
+
<v-col cols="2">
|
|
316
|
+
<v-select density="compact" v-model="feedType"
|
|
317
|
+
:items="feedTypes"
|
|
318
|
+
persistent-hint hide-details single-line>
|
|
319
|
+
</v-select>
|
|
320
|
+
</v-col>
|
|
321
|
+
<v-col cols="1">
|
|
322
|
+
<v-combobox density="compact" v-model="country"
|
|
323
|
+
:items="countries"
|
|
324
|
+
persistent-hint hide-details single-line>
|
|
325
|
+
</v-combobox>
|
|
326
|
+
</v-col>
|
|
327
|
+
</template>
|
|
328
|
+
<v-col cols="4">
|
|
269
329
|
<v-text-field v-model="query" hide-details density="compact"></v-text-field>
|
|
270
330
|
</v-col>
|
|
271
|
-
<v-col cols="
|
|
331
|
+
<v-col cols="2">
|
|
272
332
|
<v-text-field v-model="limit" hide-details type="number" density="compact"></v-text-field>
|
|
273
333
|
</v-col>
|
|
274
334
|
<v-col cols="1">
|
|
275
|
-
<v-btn icon="$search" class="bg-media_head" variant="tonal" @click="onSearch">
|
|
276
|
-
|
|
335
|
+
<v-btn icon="$search" class="bg-media_head" variant="tonal" density="default" @click="onSearch"></v-btn>
|
|
336
|
+
</v-col>
|
|
337
|
+
<v-col cols="1">
|
|
338
|
+
<v-btn icon="$stop" class="bg-media_head" variant="tonal" density="default" @click="stopAll"></v-btn>
|
|
277
339
|
</v-col>
|
|
278
340
|
</v-row>
|
|
279
341
|
</v-container>
|
|
280
342
|
<v-container v-else fluid>
|
|
281
|
-
<v-row class="align-center">
|
|
343
|
+
<v-row class="align-center" density="compact">
|
|
282
344
|
<v-col cols="1">
|
|
283
|
-
<v-btn icon="$back" class="bg-media_head" variant="tonal" @click="listBack">
|
|
284
|
-
</v-btn>
|
|
345
|
+
<v-btn icon="$back" class="bg-media_head" variant="tonal" density="compact" @click="listBack"></v-btn>
|
|
285
346
|
</v-col>
|
|
286
347
|
<v-col cols="1">
|
|
287
348
|
<v-img :src="selectedFeed!.imageUrl"></v-img>
|
|
288
349
|
</v-col>
|
|
289
350
|
<v-col cols="1">{{selectedFeed!.country}}</v-col>
|
|
290
|
-
<v-col cols="2">{{selectedFeed!.genre}}
|
|
351
|
+
<v-col cols="2">{{firstGenre(selectedFeed!.genre)}}
|
|
352
|
+
<v-tooltip v-if="!isMobile && selectedFeed!.genre && selectedFeed!.genre.indexOf('|') > 0" activator="parent" location="top">
|
|
353
|
+
{{selectedFeed!.genre.replaceAll('|', ', ')}}
|
|
354
|
+
</v-tooltip>
|
|
355
|
+
</v-col>
|
|
291
356
|
<v-col cols="2">{{selectedFeed!.owner}}</v-col>
|
|
292
|
-
<v-col cols="4">{{selectedFeed!.title}}</v-col>
|
|
293
|
-
<v-col cols="1">
|
|
357
|
+
<v-col :cols="(appConfig.isLocal && isMobile) ? 3 : 4">{{selectedFeed!.title}}</v-col>
|
|
358
|
+
<v-col v-if="appConfig.isLocal" :cols="isMobile ? 2 : 1">
|
|
294
359
|
<v-select v-model="currentPlayer" density="compact" :items="playerNames" persistent-hint
|
|
295
360
|
@update:modelValue="onPlayerChange" hide-details single-line>
|
|
296
361
|
</v-select>
|
|
297
362
|
</v-col>
|
|
298
363
|
</v-row>
|
|
299
|
-
<v-row v-if="playingItem" class="align-center">
|
|
300
|
-
<v-col cols="
|
|
301
|
-
<v-btn :icon="paused ? '$play' : '$pause'" class="bg-media_head" variant="tonal" @click="playpause"></v-btn>
|
|
302
|
-
<v-btn
|
|
303
|
-
<v-btn icon="$prev" class="bg-media_head" variant="tonal" @click="previous"></v-btn>
|
|
304
|
-
<v-btn icon="$next" class="bg-media_head" variant="tonal" @click="next"></v-btn>
|
|
364
|
+
<v-row v-if="playingItem" class="align-center" density="compact">
|
|
365
|
+
<v-col :cols="isMobile ? 5 : 3">
|
|
366
|
+
<v-btn :icon="paused ? '$play' : '$pause'" class="bg-media_head" variant="tonal" density="compact" @click="playpause"></v-btn>
|
|
367
|
+
<v-btn icon="$stop" class="bg-media_head" variant="tonal" density="compact" @click="stop"></v-btn>
|
|
368
|
+
<v-btn icon="$prev" class="bg-media_head" variant="tonal" density="compact" @click="previous"></v-btn>
|
|
369
|
+
<v-btn icon="$next" class="bg-media_head" variant="tonal" density="compact" @click="next"></v-btn>
|
|
305
370
|
</v-col>
|
|
306
|
-
<v-col cols ="
|
|
371
|
+
<v-col :cols ="isMobile? 7 : 9">
|
|
307
372
|
<v-slider v-if="!playLocal" style="width:30%" color="red" track-color="blue" track-fill-color="red" v-model="volume" hide-details density="compact"
|
|
308
373
|
min="0" max="100" step="5" @update:modelValue="changeVolume">
|
|
309
374
|
</v-slider>
|
|
310
375
|
<v-div v-else>{{playingItem.title}}</v-div>
|
|
311
376
|
</v-col>
|
|
312
377
|
</v-row>
|
|
313
|
-
<v-row v-if="playingItem">
|
|
378
|
+
<v-row v-if="playingItem" density="compact">
|
|
314
379
|
<v-col cols="12">
|
|
315
380
|
<v-progress-linear v-model="positionLength" color="blue" height="25"><strong>{{positionText}}</strong></v-progress-linear>
|
|
316
381
|
</v-col>
|
|
@@ -319,69 +384,35 @@
|
|
|
319
384
|
</v-card>
|
|
320
385
|
<v-card :height="listHeight" density="compact" class="overflow-y-auto bg-media">
|
|
321
386
|
<v-container v-if="search" fluid>
|
|
322
|
-
<v-row v-for="(feed,index) in feeds" :key="feed.rssUrl" @click="listFeed(feed)">
|
|
387
|
+
<v-row v-for="(feed,index) in feeds" :key="feed.rssUrl" density="compact" @click="listFeed(feed)">
|
|
323
388
|
<v-col cols="1">{{feed.country}}</v-col>
|
|
324
|
-
<v-col cols="2">{{feed.genre}}
|
|
389
|
+
<v-col cols="2">{{firstGenre(feed.genre)}}
|
|
390
|
+
<v-tooltip v-if="!isMobile && feed.genre && feed.genre.indexOf('|') > 0" activator="parent" location="top">
|
|
391
|
+
{{feed.genre.replaceAll('|', ', ')}}
|
|
392
|
+
</v-tooltip>
|
|
393
|
+
</v-col>
|
|
325
394
|
<v-col cols="2">{{feed.owner}}</v-col>
|
|
326
|
-
<v-col cols="5">{{feed.title}}
|
|
395
|
+
<v-col cols="5">{{feed.title}}
|
|
396
|
+
<v-tooltip v-if="!isMobile && feed.description" activator="parent" location="top">
|
|
397
|
+
<div v-html="feed.description"></div>
|
|
398
|
+
</v-tooltip>
|
|
399
|
+
</v-col>
|
|
327
400
|
</v-row>
|
|
328
401
|
</v-container>
|
|
329
|
-
<v-container v-else>
|
|
330
|
-
<v-row v-for="(item,index) in items" :key="item.title" :class="{ active: index == playIndex }" @click="listItem(item)">
|
|
331
|
-
<v-col cols="
|
|
332
|
-
|
|
402
|
+
<v-container v-else fluid>
|
|
403
|
+
<v-row v-for="(item,index) in items" :key="item.title" density="compact" :class="{ active: index == playIndex }" @click="listItem(item)">
|
|
404
|
+
<v-col cols="8">{{item.title}}
|
|
405
|
+
<v-tooltip v-if="!isMobile && item.description" activator="parent" location="top">
|
|
406
|
+
<div v-html="item.description"></div>
|
|
407
|
+
</v-tooltip>
|
|
408
|
+
</v-col>
|
|
409
|
+
<v-col cols="2">{{toTime(item.duration)}}</v-col>
|
|
410
|
+
<v-col cols="2">
|
|
411
|
+
<v-btn icon="$download" class="bg-media" density="compact" variant="flat" @click.stop="download(item)"></v-btn>
|
|
412
|
+
</v-col>
|
|
333
413
|
</v-row>
|
|
334
414
|
</v-container>
|
|
335
415
|
</v-card>
|
|
336
|
-
|
|
337
|
-
<!--
|
|
338
|
-
<v-card class="bg-media_head">
|
|
339
|
-
<audio ref="audio" preload="none" @ended="onEnded" @timeupdate="onTimeUpdate">
|
|
340
|
-
</audio>
|
|
341
|
-
<v-list-item lines="three">
|
|
342
|
-
<v-list-item-content>
|
|
343
|
-
<v-list-item-title text-h6>{{selected?.title}}</v-list-item-title>
|
|
344
|
-
<v-list-item-subtitle>{{toSubTitle(selected!)}}</v-list-item-subtitle>
|
|
345
|
-
</v-list-item-content>
|
|
346
|
-
<template v-slot:append>
|
|
347
|
-
<v-select v-model="currentPlayer" density="compact"
|
|
348
|
-
:items="playerNames"
|
|
349
|
-
persistent-hint
|
|
350
|
-
@update:modelValue="onPlayerChange"
|
|
351
|
-
hide-details single-line>
|
|
352
|
-
</v-select>
|
|
353
|
-
</template>
|
|
354
|
-
</v-list-item>
|
|
355
|
-
<v-card-actions>
|
|
356
|
-
<v-btn v-if="backVisible" @click="listBack">
|
|
357
|
-
<v-icon icon="$back" />
|
|
358
|
-
</v-btn>
|
|
359
|
-
<v-btn size="small" v-if="playingFeed" @click="playpause">
|
|
360
|
-
<v-icon v-if="paused" icon="$play" />
|
|
361
|
-
<v-icon v-else icon="$pause" />
|
|
362
|
-
</v-btn>
|
|
363
|
-
<v-btn size="small" v-if="playingFeed" @click="previous">
|
|
364
|
-
<v-icon icon="$prev" />
|
|
365
|
-
</v-btn>
|
|
366
|
-
<v-btn size="small" v-if="playingFeed" @click="next">
|
|
367
|
-
<v-icon icon="$next" />
|
|
368
|
-
</v-btn>
|
|
369
|
-
<v-slider v-if="!playLocal && playingFeed" style="width:30%" color="red" track-color="blue" track-fill-color="red" v-model="volume" hide-details density="compact"
|
|
370
|
-
min="0" max="100" step="5" @update:modelValue="changeVolume">
|
|
371
|
-
</v-slider>
|
|
372
|
-
</v-card-actions>
|
|
373
|
-
<v-progress-linear v-if="playingFeed" v-model="positionLength" color="blue" height="25"><strong>{{positionText}}</strong></v-progress-linear>
|
|
374
|
-
</v-card>
|
|
375
|
-
<v-card :height="listHeight" density="compact" class="overflow-y-auto bg-media">
|
|
376
|
-
<v-list lines="two" class="bg-media">
|
|
377
|
-
<v-list-item-group v-model="itemIndex">
|
|
378
|
-
<v-list-item v-for="(feed,index) in feeds" :key="feed.title" density="compact" :title="feed.title" :subtitle="toSubTitle(feed)"
|
|
379
|
-
active-color="blue" :active="index == playIndex" @click="listItem(feed)">
|
|
380
|
-
</v-list-item>
|
|
381
|
-
</v-list-item-group>
|
|
382
|
-
</v-list>
|
|
383
|
-
</v-card>
|
|
384
|
-
-->
|
|
385
416
|
</template>
|
|
386
417
|
|
|
387
418
|
<style scoped>
|