Последняя версия с сервера прошлого разработчика
This commit is contained in:
315
resources/js/Shared/AudioPlayer.vue
Executable file
315
resources/js/Shared/AudioPlayer.vue
Executable file
@@ -0,0 +1,315 @@
|
||||
<template>
|
||||
<div class="col-span-7 md:col-span-5 lg:col-span-3 player-widget contain-content">
|
||||
<div
|
||||
ref="topbar"
|
||||
class="
|
||||
player-line
|
||||
rounded-md
|
||||
transition-colors
|
||||
bg-transparent
|
||||
hover:bg-orange-min
|
||||
flex
|
||||
items-center
|
||||
space-x-3
|
||||
p-2
|
||||
cursor-pointer
|
||||
"
|
||||
@click="openFull"
|
||||
>
|
||||
<button class="focus:outline-none text-gray-600 hover:text-gray-800" @click.stop="skipTrack('prev')">
|
||||
<svg
|
||||
class="w-4 h-4"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
>
|
||||
<polygon points="19 20 9 12 19 4 19 20"></polygon>
|
||||
<line x1="5" y1="19"
|
||||
x2="5" y2="5"
|
||||
></line>
|
||||
</svg>
|
||||
</button>
|
||||
<button
|
||||
class="
|
||||
flex
|
||||
h-8
|
||||
items-center
|
||||
justify-center
|
||||
w-8
|
||||
transition-colors
|
||||
text-gray-600
|
||||
hover:text-gray-800
|
||||
"
|
||||
@click.stop="toggleAudio"
|
||||
>
|
||||
<PlayIcon v-show="!playing" class="w-8 h-8" />
|
||||
<StopIcon v-show="playing" class="w-8 h-8" />
|
||||
</button>
|
||||
<button class="focus:outline-none text-gray-600 hover:text-gray-800" @click.stop="skipTrack('next')">
|
||||
<svg
|
||||
class="w-4 h-4"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
>
|
||||
<polygon points="5 4 15 12 5 20 5 4"></polygon>
|
||||
<line x1="19" y1="5"
|
||||
x2="19" y2="19"
|
||||
></line>
|
||||
</svg>
|
||||
</button>
|
||||
<div v-show="count_playlist" class="text-base truncate select-none">
|
||||
{{ currentSong.name }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<teleport to="body">
|
||||
<div v-if="open_drop">
|
||||
<div
|
||||
style="
|
||||
position: fixed;
|
||||
top: 0;
|
||||
right: 0;
|
||||
left: 0;
|
||||
bottom: 0;
|
||||
z-index: 9998;
|
||||
background: black;
|
||||
opacity: 0.2;
|
||||
"
|
||||
@click="open_drop = false"
|
||||
/>
|
||||
<div
|
||||
ref="dropdown"
|
||||
class="z-[9999] player-widget-list w-full lg:w-[48rem] "
|
||||
>
|
||||
<div class="shadow-classic rounded-md bg-indigo-200">
|
||||
<div
|
||||
v-show="count_playlist"
|
||||
class="overflow-hidden bg-orange relative h-2 mt-2 mb-2"
|
||||
@click.prevent="updateSeek"
|
||||
>
|
||||
<div
|
||||
:style="{ transform: `translate3d(${playerProgress}, 0, 0)` }"
|
||||
class="will-change-transform absolute transition-transform h-full bg-white flex items-center justify-end w-full"
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div
|
||||
class="
|
||||
p-2
|
||||
lg:p-4
|
||||
rounded-md
|
||||
items-center
|
||||
grid grid-cols-1
|
||||
md:grid-cols-10
|
||||
cursor-pointer
|
||||
"
|
||||
>
|
||||
<div class="col-span-7 flex items-center space-x-3">
|
||||
<button class="focus:outline-none text-gray" @click.stop="skipTrack('prev')">
|
||||
<svg
|
||||
class="w-4 h-4"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
>
|
||||
<polygon points="19 20 9 12 19 4 19 20"></polygon>
|
||||
<line x1="5" y1="19"
|
||||
x2="5" y2="5"
|
||||
></line>
|
||||
</svg>
|
||||
</button>
|
||||
<button
|
||||
class="
|
||||
flex
|
||||
h-8
|
||||
items-center
|
||||
justify-center
|
||||
w-8
|
||||
transition-colors
|
||||
text-gray
|
||||
"
|
||||
@click.stop="toggleAudio"
|
||||
>
|
||||
<PlayIcon v-show="!playing" class="w-8 h-8" />
|
||||
<StopIcon v-show="playing" class="w-8 h-8" />
|
||||
</button>
|
||||
<button class="focus:outline-none text-gray" @click.stop="skipTrack('next')">
|
||||
<svg
|
||||
class="w-4 h-4"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
>
|
||||
<polygon points="5 4 15 12 5 20 5 4"></polygon>
|
||||
<line x1="19" y1="5"
|
||||
x2="19" y2="19"
|
||||
></line>
|
||||
</svg>
|
||||
</button>
|
||||
<div class="text-gray-light text-base truncate select-none">
|
||||
{{ currentSong.name }}
|
||||
</div>
|
||||
</div>
|
||||
<div v-show="count_playlist" class="col-span-1 text-center text-gray-light text-xs select-none">
|
||||
{{ seek }}
|
||||
</div>
|
||||
<div v-show="count_playlist" class="col-span-2 mt-2 md:mt-0 md:ml-auto flex items-center">
|
||||
<input v-model="volume" class="w-full custom-input-range"
|
||||
type="range" max="1"
|
||||
step="0.1" @click.stop=""
|
||||
@input="updateVolume(volume)"
|
||||
/>
|
||||
<span class="text-gray-light ml-1.5 text-xs">{{ volume * 100 + "%" }}</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="choices-tabs">
|
||||
<div class="border-b border-indigo-300">
|
||||
<nav class="-mb-px flex" aria-label="Tabs">
|
||||
<a v-for="tab in tabs" :key="tab.key"
|
||||
href="#" :class="[
|
||||
current_tab === tab.key ? 'border-orange text-white' : 'border-transparent text-gray-light hover:text-white',
|
||||
'w-1/2 lg:w-1/4 py-3 lg:py-4 px-1 text-center text-sm border-b-2',
|
||||
]"
|
||||
@click.prevent="changeTab(tab.key)"
|
||||
>{{ tab.name }}</a>
|
||||
</nav>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<keep-alive>
|
||||
<component :is="currentTabComponent"></component>
|
||||
</keep-alive>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</teleport>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import Popper from 'popper.js'
|
||||
import { PlayIcon, StopIcon } from '@heroicons/vue/solid'
|
||||
import { mapActions, mapGetters, mapState } from 'vuex'
|
||||
|
||||
import AudioTabNow from '@/Shared/Tabs/AudioTabNow.vue'
|
||||
import AudioTabFavorite from '@/Shared/Tabs/AudioTabFavorite.vue'
|
||||
import AudioTabLoaded from '@/Shared/Tabs/AudioTabLoaded.vue'
|
||||
|
||||
export default {
|
||||
name: 'Player',
|
||||
components: {
|
||||
AudioTabNow,
|
||||
AudioTabLoaded,
|
||||
AudioTabFavorite,
|
||||
PlayIcon,
|
||||
StopIcon
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
tabs: [
|
||||
{key: 'now', name: 'Текущая'},
|
||||
{key: 'loaded', name: 'Загруженная'},
|
||||
{key: 'favorite', name: 'Понравившийся'},
|
||||
],
|
||||
open_drop: false,
|
||||
popper: null,
|
||||
volume: 0.5,
|
||||
}
|
||||
},
|
||||
|
||||
computed: {
|
||||
currentTabComponent() {
|
||||
return 'audio-tab-' + this.current_tab
|
||||
},
|
||||
...mapGetters(['playing', 'count_playlist', 'volume_step']),
|
||||
...mapState({
|
||||
current_tab: (state) => state.player.tab,
|
||||
seek: (state) => state.player.seek,
|
||||
duration: (state) => state.player.duration,
|
||||
playerProgress: (state) => state.player.playerProgress,
|
||||
currentSong: (state) => state.player.currentSong,
|
||||
}),
|
||||
},
|
||||
|
||||
watch: {
|
||||
open_drop(open_drop) {
|
||||
if (open_drop) {
|
||||
this.$nextTick(() => {
|
||||
if (window.matchMedia('(min-width: 1024px)').matches) {
|
||||
this.popper = new Popper(this.$refs.topbar, this.$refs.dropdown, {
|
||||
placement: 'bottom-start',
|
||||
modifiers: {
|
||||
preventOverflow: { boundariesElement: 'scrollParent' },
|
||||
},
|
||||
})
|
||||
}else {
|
||||
this.popper = new Popper(this.$refs.topbar, this.$refs.dropdown, {
|
||||
placement: 'bottom-end',
|
||||
modifiers: {
|
||||
preventOverflow: {
|
||||
boundariesElement: 'scrollParent',
|
||||
padding: 0,
|
||||
},
|
||||
offset: {
|
||||
enabled: true,
|
||||
offset: '0, 10'
|
||||
}
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
})
|
||||
} else if (this.popper) {
|
||||
setTimeout(() => this.popper.destroy(), 100)
|
||||
}
|
||||
},
|
||||
},
|
||||
|
||||
created() {
|
||||
this.loadExsitPlaylist()
|
||||
this.changeVolume(this.volume_step)
|
||||
this.volume = this.volume_step
|
||||
},
|
||||
|
||||
methods: {
|
||||
|
||||
...mapActions([
|
||||
'toggleAudio',
|
||||
'updateSeek',
|
||||
'skipTrack',
|
||||
'changeVolume',
|
||||
'tabName',
|
||||
'loadExsitPlaylist',
|
||||
]),
|
||||
|
||||
openFull() {
|
||||
this.open_drop = !this.open_drop
|
||||
},
|
||||
|
||||
updateVolume(volume) {
|
||||
this.changeVolume(volume)
|
||||
},
|
||||
|
||||
changeTab(name){
|
||||
this.tabName(name)
|
||||
},
|
||||
|
||||
},
|
||||
}
|
||||
</script>
|
||||
Reference in New Issue
Block a user