Newer
Older
Eliot Berriot
committed
<template>
<main class="main pusher" v-title="labels.title">
<section :class="['ui', 'head', {'with-background': banner}, 'vertical', 'center', 'aligned', 'stripe', 'segment']" :style="headerStyle">
<div class="segment-content">
<h1 class="ui center aligned large header">
<translate translate-context="Content/Home/Header"
:translate-params="{podName: podName}">
Welcome to %{ podName }!
</translate>
<div v-if="shortDescription" class="sub header">
{{ shortDescription }}
</div>
Eliot Berriot
committed
</h1>
</div>
</section>
<section class="ui vertical stripe segment">
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
<div class="ui stackable grid">
<div class="ten wide column">
<h3 class="header">
<translate translate-context="Content/Home/Header">About this Funkwhale pod</translate>
</h3>
<div class="ui raised segment" id="pod">
<div class="ui stackable grid">
<div class="eight wide column">
<p v-if="!truncatedDescription">
<translate translate-context="Content/Home/Paragraph">No description available.</translate>
</p>
<template v-if="truncatedDescription || rules">
<div v-if="truncatedDescription" v-html="truncatedDescription"></div>
<div v-if="truncatedDescription" class="ui hidden divider"></div>
<div class="ui relaxed list">
<div class="item" v-if="truncatedDescription">
<i class="arrow right grey icon"></i>
<div class="content">
<router-link class="ui link" :to="{name: 'about'}">
<translate translate-context="Content/Home/Link">Learn more</translate>
</router-link>
</div>
</div>
<div class="item" v-if="rules">
<i class="book open grey icon"></i>
<div class="content">
<router-link class="ui link" v-if="rules" :to="{name: 'about', hash: '#rules'}">
<translate translate-context="Content/Home/Link">Server rules</translate>
</router-link>
</div>
</div>
</div>
</template>
</div>
<div class="eight wide column">
<template v-if="stats">
<h3 class="sub header">
<translate translate-context="Content/Home/Header">Statistics</translate>
</h3>
<p>
<i class="user grey icon"></i><translate translate-context="Content/Home/Stat" :translate-params="{count: stats.users.toLocaleString($store.state.ui.momentLocale) }" :translate-n="stats.users" translate-plural="%{ count } active users">%{ count } active user</translate>
</p>
<p>
<i class="music grey icon"></i><translate translate-context="Content/Home/Stat" :translate-params="{count: parseInt(stats.hours).toLocaleString($store.state.ui.momentLocale)}" :translate-n="parseInt(stats.hours)" translate-plural="%{ count } hours of music">%{ count } hour of music</translate>
</p>
</template>
<template v-if="contactEmail">
<h3 class="sub header">
<translate translate-context="Content/Home/Header/Name">Contact</translate>
</h3>
<i class="at grey icon"></i>
<a :href="`mailto:${contactEmail}`">{{ contactEmail }}</a>
</template>
</div>
Eliot Berriot
committed
</div>
</div>
</div>
<div class="six wide column">
<img class="ui image" src="../assets/network.png" />
Eliot Berriot
committed
</div>
</div>
<div class="ui hidden divider"></div>
<div class="ui hidden divider"></div>
<div class="ui stackable grid">
<div class="four wide column">
<h3 class="header">
<translate translate-context="Footer/*/Title/Short">About Funkwhale</translate>
</h3>
<p v-translate translate-context="Content/Home/Paragraph">This pod runs Funkwhale, a community-driven project that lets you listen and share music and audio within a decentralized, open network.</p>
<p v-translate translate-context="Content/Home/Paragraph">Funkwhale is free and developped by a friendly community of volunteers.</p>
<a target="_blank" rel="noopener" href="https://funkwhale.audio">
<i class="external alternate icon"></i>
<translate translate-context="Content/Home/Link">Visit funkwhale.audio</translate>
</a>
Eliot Berriot
committed
</div>
<div class="four wide column">
<h3 class="header">
<translate translate-context="Head/Login/Title">Log In</translate>
</h3>
<login-form button-classes="basic green" :show-signup="false"></login-form>
<div class="ui hidden clearing divider"></div>
</div>
<div class="four wide column">
<h3 class="header">
<translate translate-context="*/Signup/Title">Sign up</translate>
</h3>
<template v-if="openRegistrations">
<p>
<translate translate-context="Content/Home/Paragraph">Sign up now to keep a track of your favorites, create playlists, discover new content and much more!</translate>
</p>
<p v-if="defaultUploadQuota">
<translate translate-context="Content/Home/Paragraph" :translate-params="{quota: humanSize(defaultUploadQuota * 1000 * 1000)}">Users on this pod also get %{ quota } of free storage to upload their own content!</translate>
</p>
<signup-form button-classes="basic green" :show-login="false"></signup-form>
</template>
<div v-else>
<p translate-context="Content/Home/Paragraph">Registrations are closed on this pod. You can signup on another pod using the link below.</p>
<a target="_blank" rel="noopener" href="https://funkwhale.audio/#get-started">
<i class="external alternate icon"></i>
<translate translate-context="Content/Home/Link">Find another pod</translate>
</a>
Eliot Berriot
committed
</div>
</div>
<div class="four wide column">
<h3 class="header">
<translate translate-context="Content/Home/Header">Useful links</translate>
</h3>
<div class="ui relaxed list">
<div class="item">
<i class="headphones icon"></i>
<div class="content">
<router-link v-if="anonymousCanListen" class="header" to="/library">
<translate translate-context="Content/Home/Link">Browse public content</translate>
</router-link>
<div class="description">
<translate translate-context="Content/Home/Link">Listen to public albums and playlists shared on this pod</translate>
</div>
</div>
Eliot Berriot
committed
</div>
<div class="item">
<i class="mobile alternate icon"></i>
<div class="content">
<a class="header" href="https://funkwhale.audio/apps" target="_blank" rel="noopener">
<translate translate-context="Content/Home/Link">Mobile apps</translate>
</a>
<div class="description">
<translate translate-context="Content/Home/Link">Use Funkwhale on other devices with our apps</translate>
</div>
</div>
Eliot Berriot
committed
</div>
<div class="item">
<i class="book icon"></i>
<div class="content">
<a class="header" href="https://docs.funkwhale.audio/users/index.html" target="_blank" rel="noopener">
<translate translate-context="Content/Home/Link">User guides</translate>
</a>
<div class="description">
<translate translate-context="Content/Home/Link">Discover everything you need to know about Funkwhale and its features</translate>
</div>
</div>
Eliot Berriot
committed
</div>
</div>
</div>
</div>
</section>
<section v-if="anonymousCanListen" class="ui vertical stripe segment">
<album-widget :filters="{playable: true, ordering: '-creation_date'}" :limit="10">
<template slot="title"><translate translate-context="Content/Home/Title">Recently added albums</translate></template>
<router-link to="/library">
<translate translate-context="Content/Home/Link">View more…</translate>
<div class="ui hidden divider"></div>
</router-link>
</album-widget>
</section>
</main>
Eliot Berriot
committed
</template>
<script>
import $ from 'jquery'
import _ from '@/lodash'
import {mapState} from 'vuex'
import showdown from 'showdown'
import AlbumWidget from "@/components/audio/album/Widget"
import LoginForm from "@/components/auth/LoginForm"
import SignupForm from "@/components/auth/SignupForm"
import {humanSize } from '@/filters'
Eliot Berriot
committed
export default {
components: {
AlbumWidget,
LoginForm,
SignupForm,
},
data () {
markdown: new showdown.Converter(),
excerptLength: 2, // html nodes,
humanSize
...mapState({
nodeinfo: state => state.instance.nodeinfo,
}),
labels() {
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
podName() {
return _.get(this.nodeinfo, 'metadata.nodeName') || "Funkwhale"
},
banner () {
return _.get(this.nodeinfo, 'metadata.banner')
},
shortDescription () {
return _.get(this.nodeinfo, 'metadata.shortDescription')
},
longDescription () {
return _.get(this.nodeinfo, 'metadata.longDescription')
},
rules () {
return _.get(this.nodeinfo, 'metadata.rules')
},
truncatedDescription () {
if (!this.longDescription) {
return
}
let doc = this.markdown.makeHtml(this.longDescription)
let nodes = $.parseHTML(doc)
let excerptParts = []
let handled = 0
nodes.forEach((n) => {
let content = n.innerHTML || n.nodeValue
if (handled < this.excerptLength && content.trim()) {
excerptParts.push(n)
handled += 1
}
})
return excerptParts.map((p) => { return p.outerHTML }).join('')
},
stats () {
let data = {
users: _.get(this.nodeinfo, 'usage.users.activeMonth', null),
hours: _.get(this.nodeinfo, 'metadata.library.music.hours', null),
}
if (data.users === null || data.artists === null) {
return
}
return data
},
contactEmail () {
return _.get(this.nodeinfo, 'metadata.contactEmail')
},
defaultUploadQuota () {
return _.get(this.nodeinfo, 'metadata.defaultUploadQuota')
},
anonymousCanListen () {
return _.get(this.nodeinfo, 'metadata.library.anonymousCanListen')
},
openRegistrations () {
return _.get(this.nodeinfo, 'openRegistrations')
},
headerStyle() {
if (!this.banner) {
return ""
}
return (
"background-image: url(" +
this.$store.getters["instance/absoluteUrl"](this.banner) +
")"
)
},
},
watch: {
'$store.state.auth.authenticated': {
handler (v) {
if (v) {
console.log('Authenticated, redirecting to /library…')
this.$router.push('/library')
}
},
immediate: true
}
Eliot Berriot
committed
}
Eliot Berriot
committed
}
</script>
<!-- Add "scoped" attribute to limit CSS to this component only -->
@import "../style/vendor/media";
Eliot Berriot
committed
padding: 0;
}
text-shadow: 1px 1px 2px rgba(0,0,0,.8);
color: #fff !important;
}
h1.ui.header {
@include media(">tablet") {
font-size: 3em;
}
}
h1.ui.header .sub.header {
font-size: 0.8em;
}
.main.pusher {
margin-top: 0;
min-height: 10em;
}
section.segment.head {
padding: 8em 3em;
background: linear-gradient(90deg, rgba(40,88,125,1) 0%, rgba(64,130,180,1) 100%);
background-repeat: no-repeat;
background-size: cover;
}
#pod {
font-size: 110%;
display: block;
}