190 lines
6.6 KiB
Vue
190 lines
6.6 KiB
Vue
<template>
|
|
<div id="welcome" ref="welcome" @scroll="loadNextPage">
|
|
<div id="welcomeLeft" class="flex-column grow">
|
|
<div id="banner" class="center flex-column shadow">
|
|
<div id="collage">
|
|
<svg width="100%" height="100%" viewBox="20 40 600 100">
|
|
<g>
|
|
<animateTransform id="animY1" attributeName="transform" type="translate" begin="0s; animY2.end" from="0 -140" to="-20 -60" dur="30s" />
|
|
<animateTransform id="animY2" attributeName="transform" type="translate" begin="animY1.end" from="-20 -60" to="0 -140" dur="30s" />
|
|
<image :xlink:href="item.covers.cover64" :x="Math.floor(i / 6) * 64" :y="i % 6 * 64" width="64" height="64" v-for="(item, i) in randomCovers" :key="item" />
|
|
</g>
|
|
</svg>
|
|
</div>
|
|
<div class="flex-column" style="z-index: 1;">
|
|
<h1>WebPlay</h1>
|
|
</div>
|
|
</div>
|
|
<MessageScreen title="First Run?" subtitle="You still don't have any Music or Video content on your instance" icon="sync" :commands="messageCommands" @commandClicked="messageCommand" :showCommands="$store.getters['user/isAdministrator']" v-if="serverInfo.stats.tracks == 0 && serverInfo.stats.videos == 0" />
|
|
<MessageScreen v-else-if="mostListened.length == 0 && mostViewed.length == 0" title="Still no history or trends" subtitle="Still no history or trends on this instance" icon="info" />
|
|
<template v-else>
|
|
<h2 class="ma-left ma-top pa-top ma4-bottom" v-if="history.length > 0">
|
|
Last played
|
|
</h2>
|
|
<template v-if="history.length > 0">
|
|
<div id="history" :class="{ more: historyAll == true }">
|
|
<template v-for="item in history">
|
|
<AlbumItem class="ma8" v-if="item.type == 'album'" :item="item" :key="item._id" />
|
|
<ArtistItem class="ma8" v-if="item.type == 'artist'" :item="item" :key="item._id" />
|
|
<BoxItem class="ma8" v-if="item.type == 'box'" :item="item" :key="item._id" />
|
|
<RadioItem class="ma8" v-if="item.type == 'radio'" :item="item" :key="item._id" />
|
|
</template>
|
|
</div>
|
|
|
|
<span class="pa-top pa-right right" @click="toggleHistory">
|
|
<awesome-icon :icon="historyAll ? 'arrow-up' : 'arrow-down'" class="pa8-right" />{{ historyToggleText }}</span>
|
|
</template>
|
|
<div id="mostUsed" class="flex-row ma">
|
|
<div id="mostListened" class="grow" v-if="mostListened.length > 0">
|
|
<h2 class="ma-top pa-top ma4-bottom">Most listened</h2>
|
|
<div class="flex-column">
|
|
<TrackItem v-for="(item, i) in mostListened" :track="item" :key="i" />
|
|
</div>
|
|
</div>
|
|
<div id="mostViewed" class="grow" v-if="mostViewed.length > 0">
|
|
<h2 class="ma-top pa-top ma4-bottom">Most viewed</h2>
|
|
<div id="mostViewedVideos" class="flex-row">
|
|
<VideoItem v-for="(item, i) in mostViewed" :video="item" :key="i" />
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</template>
|
|
</div>
|
|
<div v-if="newestAlbums.length > 0 || newestBoxes.length > 0" id="newest" class="pa-left pa-right">
|
|
<template v-if="newestAlbums.length > 0">
|
|
<h3>Newest Music</h3>
|
|
<div id="newestMusic" class="flex-column pa-bottom">
|
|
<AlbumItem class="ma8" v-for="item in newestAlbums" type="line" :item="item" :key="item._id" />
|
|
</div>
|
|
</template>
|
|
<template v-if="newestBoxes.length > 0">
|
|
<h3>Newest Videos</h3>
|
|
<div id="newestVideos" class="flex-row">
|
|
<BoxItem class="ma8 small" v-for="item in newestBoxes" :item="item" :key="item._id" />
|
|
</div>
|
|
</template>
|
|
</div>
|
|
</div>
|
|
</template>
|
|
<script>
|
|
import RadioItem from "../components/Radio";
|
|
import TrackItem from "../components/Track";
|
|
import VideoItem from "../components/Video";
|
|
import { mapGetters } from "vuex";
|
|
|
|
export default {
|
|
name: "HomeView",
|
|
data() {
|
|
return {
|
|
scrollPosition: 0,
|
|
historyAll: false,
|
|
messageCommands: [
|
|
{
|
|
title: "Scan for Music files",
|
|
subtitle: "Scann your server for music files…",
|
|
icon: "music",
|
|
command: "scanMusic",
|
|
},
|
|
{
|
|
title: "Scan for Video files",
|
|
subtitle: "Scann your server for video files…",
|
|
icon: "video",
|
|
command: "scanVideos",
|
|
},
|
|
],
|
|
};
|
|
},
|
|
mounted() {
|
|
this.loadItems();
|
|
},
|
|
methods: {
|
|
loadItems() {
|
|
this.$refs.welcome.scrollTop = this.scrollPosition;
|
|
this.$store.dispatch("albums/loadNewest");
|
|
this.$store.dispatch("boxes/loadNewest");
|
|
this.$store.dispatch("tracks/loadMostListened");
|
|
this.$store.dispatch("videos/loadMostViewed");
|
|
if (this.randomCovers.length == 0) {
|
|
this.$store.dispatch("albums/loadRandomCovers", 60);
|
|
this.$store.dispatch("albums/loadAlbums", true).then(() => {
|
|
this.$store.dispatch("artists/loadArtists", true).then(() => {
|
|
this.$store.dispatch("boxes/loadBoxes", true);
|
|
});
|
|
});
|
|
}
|
|
},
|
|
loadNextPage() {
|
|
this.scrollPosition = this.$refs.welcome.scrollTop;
|
|
},
|
|
messageCommand(req) {
|
|
switch (req.command) {
|
|
case "scanMusic":
|
|
this.$store.dispatch("startScanningMusic");
|
|
setTimeout(() => {
|
|
this.$store.dispatch("albums/loadAlbums", true);
|
|
this.$router.push("/albums");
|
|
}, 3000);
|
|
break;
|
|
case "scanVideos":
|
|
this.$store.dispatch("startScanningVideos");
|
|
setTimeout(() => {
|
|
this.$store.dispatch("boxes/loadBoxes", true);
|
|
this.$router.push("/boxes");
|
|
}, 3000);
|
|
break;
|
|
}
|
|
},
|
|
toggleHistory() {
|
|
this.historyAll = !this.historyAll;
|
|
},
|
|
},
|
|
computed: {
|
|
...mapGetters({
|
|
history: "user/history",
|
|
newestAlbums: "albums/newest",
|
|
newestBoxes: "boxes/newest",
|
|
serverInfo: "serverInfo",
|
|
mostListened: "tracks/mostListened",
|
|
mostViewed: "videos/mostViewed",
|
|
randomCovers: ["albums/randomCovers"],
|
|
}),
|
|
historyToggleText() {
|
|
return this.historyAll ? "less..." : "more...";
|
|
},
|
|
},
|
|
watch: {
|
|
"$route.path": function (newVal) {
|
|
if (newVal == "/") {
|
|
this.$store.dispatch("resetViewMenu", this.viewMenu);
|
|
this.$nextTick(() => {
|
|
this.loadItems();
|
|
});
|
|
}
|
|
},
|
|
},
|
|
components: {
|
|
RadioItem,
|
|
TrackItem,
|
|
VideoItem,
|
|
},
|
|
};
|
|
</script>
|
|
|
|
<style scoped>
|
|
#history.more {
|
|
max-height: initial;
|
|
}
|
|
|
|
#banner {
|
|
position: relative;
|
|
}
|
|
|
|
#collage {
|
|
bottom: 0;
|
|
top: 0;
|
|
left: 0;
|
|
right: 0;
|
|
opacity: 0.2;
|
|
position: absolute;
|
|
}
|
|
</style> |