feat: add playback speed setting (close #39)
All checks were successful
repod / xml (push) Successful in 22s
repod / php (push) Successful in 1m7s
repod / nodejs (push) Successful in 2m11s
repod / release (push) Has been skipped

This commit is contained in:
Michel Roux 2024-01-16 22:12:07 +01:00
parent 31bf193543
commit 9ebd96cec1
14 changed files with 175 additions and 68 deletions

View File

@ -19,6 +19,7 @@ OC.L10N.register(
"Delete" : "Supprimer",
"Are you sure you want to delete this subscription?" : "Êtes-vous sûr de vouloir supprimer ce flux ?",
"Error while removing the feed" : "Erreur lors de la suppression du flux",
"Playback speed" : "Vitesse de lecture",
"Add a podcast" : "Ajouter un podcast",
"Could not fetch subscriptions" : "Impossible de récupérer les flux",
"Find a podcast" : "Chercher un podcast",

View File

@ -17,6 +17,7 @@
"Delete" : "Supprimer",
"Are you sure you want to delete this subscription?" : "Êtes-vous sûr de vouloir supprimer ce flux ?",
"Error while removing the feed" : "Erreur lors de la suppression du flux",
"Playback speed" : "Vitesse de lecture",
"Add a podcast" : "Ajouter un podcast",
"Could not fetch subscriptions" : "Impossible de récupérer les flux",
"Find a podcast" : "Chercher un podcast",

View File

@ -1,22 +0,0 @@
<template>
<ul :class="episode ? 'margin' : ''">
<slot />
</ul>
</template>
<script>
export default {
name: 'AdaptativeList',
computed: {
episode() {
return this.$store.state.player.episode
},
},
}
</script>
<style scoped>
.margin {
margin-bottom: 6rem;
}
</style>

View File

@ -0,0 +1,27 @@
<template>
<NcAppContent :class="episode ? 'margin' : ''">
<slot />
</NcAppContent>
</template>
<script>
import { NcAppContent } from '@nextcloud/vue'
export default {
name: 'AppContent',
components: {
NcAppContent,
},
computed: {
episode() {
return this.$store.state.player.episode
},
},
}
</script>
<style scoped>
.margin {
padding-bottom: 6rem;
}
</style>

View File

@ -0,0 +1,33 @@
<template>
<NcAppNavigation :class="episode ? 'margin' : ''">
<slot />
<template #list>
<slot name="list" />
</template>
<template #footer>
<slot name="footer" />
</template>
</NcAppNavigation>
</template>
<script>
import { NcAppNavigation } from '@nextcloud/vue'
export default {
name: 'AppNavigation',
components: {
NcAppNavigation,
},
computed: {
episode() {
return this.$store.state.player.episode
},
},
}
</script>
<style scoped>
.margin {
padding-bottom: 6rem;
}
</style>

View File

@ -1,7 +1,7 @@
<template>
<div>
<Loading v-if="loading" />
<AdaptativeList v-if="!loading">
<ul v-if="!loading">
<NcListItem v-for="feed in feeds"
:key="feed.link"
:details="moment(feed.fetchedAtUnix*1000).fromNow()"
@ -16,13 +16,12 @@
{{ feed.author }}
</template>
</NcListItem>
</AdaptativeList>
</ul>
</div>
</template>
<script>
import { NcAvatar, NcListItem } from '@nextcloud/vue'
import AdaptativeList from '../Atoms/AdaptativeList.vue'
import Loading from '../Atoms/Loading.vue'
import axios from '@nextcloud/axios'
import { debounce } from '../../utils/debounce.js'
@ -34,7 +33,6 @@ import { toUrl } from '../../utils/url.js'
export default {
name: 'Search',
components: {
AdaptativeList,
Loading,
NcAvatar,
NcListItem,

View File

@ -1,7 +1,7 @@
<template>
<div>
<Loading v-if="loading" />
<AdaptativeList v-if="!loading">
<ul v-if="!loading">
<NcListItem v-for="episode in episodes"
:key="episode.guid"
:active="isCurrentEpisode(episode)"
@ -34,7 +34,7 @@
</NcActionButton>
</template>
</NcListItem>
</AdaptativeList>
</ul>
<NcModal v-if="modalEpisode" @close="closeModal">
<Modal :description="modalEpisode.description"
:image="modalEpisode.image"
@ -50,7 +50,6 @@
<script>
import { NcActionButton, NcAvatar, NcListItem, NcModal } from '@nextcloud/vue'
import { decodeUrl, encodeUrl } from '../../utils/url.js'
import AdaptativeList from '../Atoms/AdaptativeList.vue'
import Loading from '../Atoms/Loading.vue'
import Modal from './Modal.vue'
import PlayButton from 'vue-material-design-icons/Play.vue'
@ -63,7 +62,6 @@ import { showError } from '@nextcloud/dialogs'
export default {
name: 'Episodes',
components: {
AdaptativeList,
Loading,
Modal,
NcActionButton,

View File

@ -0,0 +1,50 @@
<template>
<NcAppNavigationSettings>
<div class="setting">
<label id="">{{ t('repod', 'Playback speed') }}</label>
<div class="buttons">
<Minus :size="20" @click="changeRate(-.5)" />
<NcCounterBubble>x{{ player.rate }}</NcCounterBubble>
<Plus :size="20" @click="changeRate(.5)" />
</div>
</div>
</NcAppNavigationSettings>
</template>
<script>
import { NcAppNavigationSettings, NcCounterBubble } from '@nextcloud/vue'
import Minus from 'vue-material-design-icons/Minus.vue'
import Plus from 'vue-material-design-icons/Plus.vue'
export default {
name: 'Settings',
components: {
Minus,
NcAppNavigationSettings,
NcCounterBubble,
Plus,
},
computed: {
player() {
return this.$store.state.player
},
},
methods: {
changeRate(diff) {
this.$store.dispatch('player/rate', this.player.rate + diff)
},
},
}
</script>
<style scoped>
.buttons {
display: flex;
gap: .5rem;
}
.setting {
display: flex;
justify-content: space-between;
}
</style>

View File

@ -1,41 +1,47 @@
<template>
<NcAppNavigation>
<NcAppContentList>
<router-link to="/">
<NcAppNavigationNew :text="t('repod', 'Add a podcast')">
<template #icon>
<Plus :size="20" />
</template>
</NcAppNavigationNew>
</router-link>
<Loading v-if="loading" />
<AdaptativeList v-if="!loading">
<Item v-for="subscriptionUrl of subscriptions"
:key="subscriptionUrl"
:url="subscriptionUrl" />
</AdaptativeList>
</NcAppContentList>
</NcAppNavigation>
<AppNavigation>
<template #list>
<NcAppContentList>
<router-link to="/">
<NcAppNavigationNew :text="t('repod', 'Add a podcast')">
<template #icon>
<Plus :size="20" />
</template>
</NcAppNavigationNew>
</router-link>
<Loading v-if="loading" />
<ul v-if="!loading">
<Item v-for="subscriptionUrl of subscriptions"
:key="subscriptionUrl"
:url="subscriptionUrl" />
</ul>
</NcAppContentList>
</template>
<template #footer>
<Settings />
</template>
</AppNavigation>
</template>
<script>
import { NcAppContentList, NcAppNavigation, NcAppNavigationNew } from '@nextcloud/vue'
import AdaptativeList from '../Atoms/AdaptativeList.vue'
import { NcAppContentList, NcAppNavigationNew } from '@nextcloud/vue'
import AppNavigation from '../Atoms/AppNavigation.vue'
import Item from './Item.vue'
import Loading from '../Atoms/Loading.vue'
import Plus from 'vue-material-design-icons/Plus.vue'
import Settings from './Settings.vue'
import { showError } from '@nextcloud/dialogs'
export default {
name: 'Subscriptions',
components: {
AdaptativeList,
AppNavigation,
Item,
Loading,
NcAppContentList,
NcAppNavigation,
NcAppNavigationNew,
Plus,
Settings,
},
data() {
return {
@ -43,9 +49,6 @@ export default {
}
},
computed: {
currentEpisode() {
return this.$store.state.player.episode
},
subscriptions() {
return this.$store.state.subscriptions.subscriptions
},

View File

@ -10,6 +10,7 @@ audio.onended = () => store.dispatch('player/stop')
audio.onloadeddata = () => store.commit('player/loaded', true)
audio.onplay = () => store.commit('player/paused', false)
audio.onpause = () => store.commit('player/paused', true)
audio.onratechange = () => store.commit('player/rate', audio.playbackRate)
audio.onseeked = () => store.commit('player/currentTime', audio.currentTime)
audio.ontimeupdate = () => store.commit('player/currentTime', audio.currentTime)
audio.onvolumechange = () => store.commit('player/volume', audio.volume)
@ -24,6 +25,7 @@ export const player = {
paused: null,
podcastUrl: null,
volume: 1,
rate: 1,
},
mutations: {
action: (state, action) => {
@ -66,6 +68,9 @@ export const player = {
volume: (state, volume) => {
state.volume = volume
},
rate: (state, rate) => {
state.rate = rate
},
},
actions: {
load: async (context, episode) => {
@ -101,6 +106,9 @@ export const player = {
volume: (_, volume) => {
audio.volume = volume
},
rate: (_, rate) => {
audio.playbackRate = rate
},
},
}

View File

@ -1,5 +1,5 @@
<template>
<NcAppContent class="main">
<AppContent class="main">
<NcTextField :label="t('repod', 'Find a podcast')" :value.sync="search">
<Magnify :size="20" />
</NcTextField>
@ -7,13 +7,14 @@
<Tops v-if="!search" type="hot" />
<Tops v-if="!search" type="new" />
<AddRss v-if="!search" />
</NcAppContent>
</AppContent>
</template>
<script>
import { NcAppContent, NcTextField } from '@nextcloud/vue'
import AddRss from '../components/Discover/AddRss.vue'
import AppContent from '../components/Atoms/AppContent.vue'
import Magnify from 'vue-material-design-icons/Magnify.vue'
import { NcTextField } from '@nextcloud/vue'
import Search from '../components/Discover/Search.vue'
import Tops from '../components/Discover/Tops.vue'
@ -21,8 +22,8 @@ export default {
name: 'Discover',
components: {
AddRss,
AppContent,
Magnify,
NcAppContent,
NcTextField,
Search,
Tops,

View File

@ -1,5 +1,5 @@
<template>
<NcAppContent>
<AppContent>
<Loading v-if="loading" />
<NcEmptyContent v-if="failed"
class="error"
@ -15,15 +15,16 @@
:link="feed.link"
:title="feed.title" />
<Episodes v-if="feed" />
</NcAppContent>
</AppContent>
</template>
<script>
import { NcAppContent, NcEmptyContent } from '@nextcloud/vue'
import Alert from 'vue-material-design-icons/Alert.vue'
import AppContent from '../components/Atoms/AppContent.vue'
import Banner from '../components/Feed/Banner.vue'
import Episodes from '../components/Feed/Episodes.vue'
import Loading from '../components/Atoms/Loading.vue'
import { NcEmptyContent } from '@nextcloud/vue'
import axios from '@nextcloud/axios'
import { generateUrl } from '@nextcloud/router'
@ -31,10 +32,10 @@ export default {
name: 'Feed',
components: {
Alert,
AppContent,
Banner,
Episodes,
Loading,
NcAppContent,
NcEmptyContent,
},
data() {

View File

@ -86,6 +86,10 @@ msgstr "Êtes-vous sûr de vouloir supprimer ce flux ?"
msgid "Error while removing the feed"
msgstr "Erreur lors de la suppression du flux"
#: /app/specialVueFakeDummyForL10nScript.js:15
msgid "Playback speed"
msgstr "Vitesse de lecture"
msgid "Add a podcast"
msgstr "Ajouter un podcast"

View File

@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: Nextcloud 3.14159\n"
"Report-Msgid-Bugs-To: translations\\@example.com\n"
"POT-Creation-Date: 2024-01-15 23:19+0000\n"
"POT-Creation-Date: 2024-01-16 21:09+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@ -98,25 +98,29 @@ msgid "Error while removing the feed"
msgstr ""
#: /app/specialVueFakeDummyForL10nScript.js:15
msgid "Add a podcast"
msgid "Playback speed"
msgstr ""
#: /app/specialVueFakeDummyForL10nScript.js:16
msgid "Could not fetch subscriptions"
msgid "Add a podcast"
msgstr ""
#: /app/specialVueFakeDummyForL10nScript.js:17
msgid "Find a podcast"
msgid "Could not fetch subscriptions"
msgstr ""
#: /app/specialVueFakeDummyForL10nScript.js:18
msgid "Error loading feed"
msgid "Find a podcast"
msgstr ""
#: /app/specialVueFakeDummyForL10nScript.js:19
msgid "Missing required app"
msgid "Error loading feed"
msgstr ""
#: /app/specialVueFakeDummyForL10nScript.js:20
msgid "Missing required app"
msgstr ""
#: /app/specialVueFakeDummyForL10nScript.js:21
msgid "Install GPodder Sync"
msgstr ""