podcasts & player
This commit is contained in:
@ -149,81 +149,13 @@ a.navbar-item.is-active {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//-- player
|
||||
.player {
|
||||
z-index: 10000;
|
||||
box-shadow: 0em 1.5em 2.5em rgba(0, 0, 0, 0.6);
|
||||
|
||||
.player-panels {
|
||||
height: 0%;
|
||||
transition: height 3s;
|
||||
}
|
||||
.player-panels.is-open {
|
||||
height: auto;
|
||||
}
|
||||
|
||||
.player-panel {
|
||||
margin: 0.4em;
|
||||
max-height: 80%;
|
||||
overflow-y: auto;
|
||||
}
|
||||
|
||||
.progress {
|
||||
margin: 0em;
|
||||
padding: 0em;
|
||||
border-color: $info;
|
||||
border-style: 'solid';
|
||||
}
|
||||
|
||||
.player-bar {
|
||||
border-top: 1px $grey-light solid;
|
||||
|
||||
> div {
|
||||
height: 3.75em !important;
|
||||
}
|
||||
|
||||
> .media-left:not(:last-child) {
|
||||
margin-right: 0em;
|
||||
}
|
||||
|
||||
> .media-cover {
|
||||
border-left: 1px black solid;
|
||||
}
|
||||
|
||||
.cover {
|
||||
font-size: 1.5rem !important;
|
||||
height: 2.5em !important;
|
||||
}
|
||||
|
||||
> .media-content {
|
||||
padding-top: 0.4em;
|
||||
padding-left: 0.4em;
|
||||
}
|
||||
|
||||
.button {
|
||||
font-size: 1.5rem !important;
|
||||
height: 100%;
|
||||
padding: auto 0.2em !important;
|
||||
min-width: 2.5em;
|
||||
border-radius: 0px;
|
||||
transition: background-color 1s;
|
||||
}
|
||||
|
||||
.title {
|
||||
margin: 0em;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//-- general
|
||||
:root {
|
||||
--text-color: black;
|
||||
--highlight-color: rgba(255, 255, 0, 1);
|
||||
--highlight-color-alpha: rgba(255, 255, 0, 0.6);
|
||||
--highlight-color-alpha: rgba(255, 255, 0, 0.7);
|
||||
--highlight-color-2: rgb(0, 0, 254);
|
||||
--highlight-color-2-alpha: rgb(0, 0, 254, 0.6);
|
||||
--highlight-color-2-alpha: rgb(0, 0, 254, 0.7);
|
||||
|
||||
--header-height: 30em;
|
||||
|
||||
@ -231,6 +163,7 @@ a.navbar-item.is-active {
|
||||
--heading-title-bg-color: rgba(255, 255, 0, 1);
|
||||
--heading-bg-color: var(--highlight-color);
|
||||
--heading-bg-highlight-color: var(--highlight-color-2);
|
||||
--heading-font-family: default;
|
||||
|
||||
--preview-media-height: 10em;
|
||||
--preview-media-cover-size: 10em;
|
||||
@ -238,7 +171,11 @@ a.navbar-item.is-active {
|
||||
--preview-cover-size: 24em;
|
||||
--preview-cover-small-size: 10em;
|
||||
|
||||
--heading-font-family: default;
|
||||
--player-panel-bg: var(--highlight-color-alpha);
|
||||
--player-bar-bg: var(--highlight-color);
|
||||
--progress-border: 1px var(--highlight-color-2) solid;
|
||||
--progress-bg-color: transparent;
|
||||
--progress-bar-color: var(--highlight-color-2);
|
||||
}
|
||||
|
||||
|
||||
@ -253,31 +190,6 @@ section > .toolbar {
|
||||
}
|
||||
|
||||
|
||||
aside {
|
||||
& > section {
|
||||
margin-bottom: 2em;
|
||||
}
|
||||
|
||||
.cover.is-small { width: 10em; }
|
||||
.cover.is-tiny { height: 2em; }
|
||||
|
||||
.media .subtitle {
|
||||
font-size: 1em;
|
||||
}
|
||||
}
|
||||
|
||||
.sound-item {
|
||||
.cover { height: 5em; }
|
||||
.media-content a { padding: 0em; }
|
||||
margin-bottom: 0.2em;
|
||||
}
|
||||
.sound-item .media-right .button {
|
||||
margin-right: 0.2em;
|
||||
min-width: 2.5em;
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
|
||||
// ---- main theme & layout
|
||||
h1, h2, h3, h4, h5, h6, .heading, .title, .subtitle {
|
||||
font-family: var(--heading-font-family);
|
||||
@ -290,6 +202,7 @@ h1, h2, h3, h4, h5, h6, .heading, .title, .subtitle {
|
||||
background-color: var(--highlight-color-alpha);
|
||||
color: var(--highlight-color-2);
|
||||
text-decoration: none;
|
||||
padding: $mp-2;
|
||||
}
|
||||
|
||||
.content {
|
||||
@ -303,11 +216,11 @@ h1, h2, h3, h4, h5, h6, .heading, .title, .subtitle {
|
||||
margin-top: unset;
|
||||
padding-top: unset !important;
|
||||
margin-bottom: $mp-4;
|
||||
border-bottom: 1px solid black;
|
||||
}
|
||||
|
||||
&:not(:first-child) {
|
||||
margin-top: $mp-6;
|
||||
border-top: 1px solid black;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -330,6 +243,7 @@ h1, h2, h3, h4, h5, h6, .heading, .title, .subtitle {
|
||||
.flex-push-right { margin-left: auto; }
|
||||
.flex-grow-0 { flex-grow: 0 !important; }
|
||||
|
||||
.no-border { border: 0px !important; }
|
||||
|
||||
.is-clickable { cursor: pointer; }
|
||||
|
||||
@ -342,17 +256,31 @@ h1, h2, h3, h4, h5, h6, .heading, .title, .subtitle {
|
||||
}
|
||||
|
||||
.button {
|
||||
&.action {
|
||||
border-radius: 0px;
|
||||
border-color: var(--highlight-color-2-alpha);
|
||||
|
||||
&:hover {
|
||||
border-color: var(--highlight-color-2) !important;
|
||||
color: var(--highlight-color-2) !important;
|
||||
opacity: 1 !important;
|
||||
}
|
||||
|
||||
.actions &, &.action {
|
||||
background-color: var(--highlight-color);
|
||||
justify-content: center;
|
||||
padding: $mp-2 !important;
|
||||
min-width: 2em;
|
||||
|
||||
.icon { margin: 0em !important; }
|
||||
.not-selected { opacity: 0.6; }
|
||||
|
||||
label {
|
||||
margin-left: $mp-2;
|
||||
}
|
||||
|
||||
&:hover, .selected {
|
||||
color: var(--highlight-color-2) !important;
|
||||
}
|
||||
}
|
||||
|
||||
.dropdown-trigger {
|
||||
@ -361,10 +289,26 @@ h1, h2, h3, h4, h5, h6, .heading, .title, .subtitle {
|
||||
}
|
||||
|
||||
|
||||
.list-filters {
|
||||
text-align: right;
|
||||
.button-group {
|
||||
.button {
|
||||
background-color: transparent;
|
||||
border-top: 0px;
|
||||
border-bottom: 0px;
|
||||
height: 100%;
|
||||
|
||||
&:last-child {
|
||||
border-right: 0px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.actions {
|
||||
&.no-label label {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
.title {
|
||||
text-transform: uppercase;
|
||||
|
||||
@ -393,12 +337,6 @@ h1, h2, h3, h4, h5, h6, .heading, .title, .subtitle {
|
||||
}
|
||||
}
|
||||
|
||||
.actions {
|
||||
&.no-label label {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.dropdown-item {
|
||||
font-size: unset !important
|
||||
}
|
||||
@ -479,7 +417,7 @@ nav li {
|
||||
.preview {
|
||||
position: relative;
|
||||
background-size: cover;
|
||||
margin-bottom: $mp-4 !important;
|
||||
margin-bottom: $mp-6 !important;
|
||||
|
||||
&.preview-card {
|
||||
&:not(.wide) {
|
||||
@ -720,3 +658,165 @@ nav li {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
// ---- player
|
||||
// -- components
|
||||
.a-progress {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
margin: 0em;
|
||||
padding: 0em;
|
||||
background-color: var(--progress-bg-color);
|
||||
|
||||
.a-progress-bar-container {
|
||||
flex-grow: 1;
|
||||
margin: 0em $mp-3;
|
||||
border: var(--progress-border);
|
||||
}
|
||||
|
||||
.a-progress-bar {
|
||||
background-color: var(--progress-bar-color);
|
||||
}
|
||||
}
|
||||
|
||||
.playlist, .a-playlist {
|
||||
.header {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
}
|
||||
|
||||
.title {
|
||||
font-size: $text-size;
|
||||
margin: 0;
|
||||
padding: $mp-3;
|
||||
}
|
||||
|
||||
li {
|
||||
list-style: none;
|
||||
border-bottom: 1px var(--highlight-color-2) solid;
|
||||
|
||||
&:last-child {
|
||||
border-bottom: 0px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// -- sound item
|
||||
.a-sound-item {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex-direction: row;
|
||||
|
||||
height: 3em;
|
||||
background-color: var(--highlight-color-alpha);
|
||||
|
||||
&.playing, &.playing .title {
|
||||
color: var(--highlight-color-2) !important;
|
||||
}
|
||||
|
||||
&:hover {
|
||||
background-color: var(--highlight-color);
|
||||
.title {
|
||||
color: var(--highlight-color-2) !important;
|
||||
}
|
||||
}
|
||||
|
||||
.headings > * {
|
||||
}
|
||||
|
||||
.title {
|
||||
.icon {
|
||||
padding: 0em $mp-3;
|
||||
}
|
||||
|
||||
margin: 0em;
|
||||
padding: 0em;
|
||||
font-size: $text-size-medium;
|
||||
}
|
||||
.button {
|
||||
width: 3em;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//-- player
|
||||
.a-player {
|
||||
z-index: 10000;
|
||||
box-shadow: 0em 1.5em 2.5em rgba(0, 0, 0, 0.6);
|
||||
|
||||
a { color: var(--highlight-color-2); }
|
||||
}
|
||||
|
||||
.a-player-panels {
|
||||
background: var(--player-panel-bg);
|
||||
height: 0%;
|
||||
transition: height 1s;
|
||||
}
|
||||
.a-player-panels.is-open {
|
||||
height: auto;
|
||||
}
|
||||
|
||||
.a-player-panel {
|
||||
padding-bottom: $mp-3;
|
||||
max-height: 80%;
|
||||
overflow-y: auto;
|
||||
|
||||
.a-sound-item:not(:hover) {
|
||||
background-color: transparent;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
.a-player-bar {
|
||||
display: flex;
|
||||
background: var(--player-bar-bg);
|
||||
flex-direction: row;
|
||||
justify-content: center;
|
||||
|
||||
border-top: 1px $grey-light solid;
|
||||
height: 3.75em !important;
|
||||
|
||||
> * { height: 100%; }
|
||||
|
||||
.cover { height: 100%; }
|
||||
.title {
|
||||
font-size: $text-size;
|
||||
margin: 0em;
|
||||
|
||||
&:last-child {
|
||||
font-size: $text-size-bigger;
|
||||
}
|
||||
}
|
||||
|
||||
.button {
|
||||
font-size: $text-size-bigger;
|
||||
height: 100%;
|
||||
padding: auto 0.2em !important;
|
||||
min-width: 2.5em;
|
||||
border-radius: 0px;
|
||||
transition: background-color 0.5s;
|
||||
|
||||
&:hover {
|
||||
color: var(--highlight-color-2) !important;
|
||||
}
|
||||
|
||||
&.active {
|
||||
color: var(--highlight-color-2);
|
||||
}
|
||||
|
||||
&.open {
|
||||
background-color: var(--highlight-color-2);
|
||||
color: var(--highlight-color);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.a-player-bar-content {
|
||||
flex-grow: 1;
|
||||
padding-top: $mp-3;
|
||||
padding-left: $mp-3;
|
||||
padding-right: $mp-3;
|
||||
}
|
||||
|
@ -25,7 +25,7 @@ $menu-item-active-background-color: #d2d2d2;
|
||||
@import "~bulma/sass/elements/icon";
|
||||
// @import "~bulma/sass/elements/image";
|
||||
// @import "~bulma/sass/elements/notification";
|
||||
@import "~bulma/sass/elements/progress";
|
||||
// @import "~bulma/sass/elements/progress";
|
||||
@import "~bulma/sass/elements/table";
|
||||
@import "~bulma/sass/elements/tag";
|
||||
@import "~bulma/sass/elements/title";
|
||||
|
@ -1,49 +1,57 @@
|
||||
<template>
|
||||
<div class="player">
|
||||
<div :class="['player-panels', panel ? 'is-open' : '']">
|
||||
<APlaylist ref="pin" class="player-panel menu" v-show="panel == 'pin' && sets.pin.length"
|
||||
<div class="a-player">
|
||||
<div :class="['a-player-panels', panel ? 'is-open' : '']">
|
||||
<APlaylist ref="pin" class="a-player-panel a-playlist" v-show="panel == 'pin' && sets.pin.length"
|
||||
name="Pinned"
|
||||
:actions="['page']"
|
||||
:editable="true" :player="self" :set="sets.pin" @select="togglePlay('pin', $event.index)"
|
||||
listClass="menu-list" itemClass="menu-item">
|
||||
<template v-slot:header="">
|
||||
<p class="menu-label">
|
||||
<span class="icon"><span class="fa fa-thumbtack"></span></span>
|
||||
<div class="title is-flex-grow-1">
|
||||
<span class="icon"><span class="fa fa-star"></span></span>
|
||||
Pinned
|
||||
</p>
|
||||
</div>
|
||||
<button class="action button no-border">
|
||||
<span class="icon" @click.stop="togglePanel()">
|
||||
<i class="fa fa-close"></i>
|
||||
</span>
|
||||
</button>
|
||||
</template>
|
||||
</APlaylist>
|
||||
<APlaylist ref="queue" class="player-panel menu" v-show="panel == 'queue' && sets.queue.length"
|
||||
<APlaylist ref="queue" class="a-player-panel a-playlist" v-show="panel == 'queue' && sets.queue.length"
|
||||
:actions="['page']"
|
||||
:editable="true" :player="self" :set="sets.queue" @select="togglePlay('queue', $event.index)"
|
||||
listClass="menu-list" itemClass="menu-item">
|
||||
<template v-slot:header="">
|
||||
<p class="menu-label">
|
||||
<div class="title is-flex-grow-1">
|
||||
<span class="icon"><span class="fa fa-list"></span></span>
|
||||
Playlist
|
||||
</p>
|
||||
</div>
|
||||
<button class="action button no-border">
|
||||
<span class="icon" @click.stop="togglePanel()">
|
||||
<i class="fa fa-close"></i>
|
||||
</span>
|
||||
</button>
|
||||
</template>
|
||||
</APlaylist>
|
||||
</div>
|
||||
|
||||
<div class="player-bar media">
|
||||
<div class="media-left">
|
||||
<button class="button" @click="togglePlay()"
|
||||
:title="buttonTitle" :aria-label="buttonTitle">
|
||||
<span class="fas fa-pause" v-if="playing"></span>
|
||||
<span class="fas fa-play" v-else></span>
|
||||
</button>
|
||||
</div>
|
||||
<div class="media-left media-cover" v-if="current && current.data.cover">
|
||||
<div class="a-player-bar button-group">
|
||||
<button class="button" @click="togglePlay()"
|
||||
:title="buttonTitle" :aria-label="buttonTitle">
|
||||
<span class="fas fa-pause" v-if="playing"></span>
|
||||
<span class="fas fa-play" v-else></span>
|
||||
</button>
|
||||
<div class="media-cover" v-if="current && current.data.cover">
|
||||
<img :src="current.data.cover" class="cover" />
|
||||
</div>
|
||||
<div class="media-content">
|
||||
<div :class="['a-player-bar-content', loaded && duration ? 'has-progress' : '']">
|
||||
<slot name="content" :loaded="loaded" :live="live" :current="current"></slot>
|
||||
<AProgress v-if="loaded && duration" :value="currentTime" :max="this.duration"
|
||||
:format="displayTime" class="pt-1 is-size-7"
|
||||
@select="audio.currentTime = $event"></AProgress>
|
||||
</div>
|
||||
<div class="media-right">
|
||||
<div>
|
||||
<button class="button has-text-weight-bold" v-if="loaded" @click="play()">
|
||||
<span class="icon is-size-6 has-text-danger">
|
||||
<span class="fa fa-circle"></span>
|
||||
@ -54,7 +62,7 @@
|
||||
@click="togglePanel('pin')" v-show="sets.pin.length">
|
||||
<span class="is-size-6" v-if="sets.pin.length">
|
||||
{{ sets.pin.length }}</span>
|
||||
<span class="icon"><span class="fa fa-thumbtack"></span></span>
|
||||
<span class="icon"><span class="fa fa-star"></span></span>
|
||||
</button>
|
||||
<button :class="playlistButtonClass('queue')"
|
||||
@click="togglePanel('queue')" v-show="sets.queue.length">
|
||||
@ -156,10 +164,9 @@ export default {
|
||||
playlistButtonClass(name) {
|
||||
let set = this.sets[name];
|
||||
return (set ? (set.length ? "" : "has-text-grey-light ")
|
||||
+ (this.panel == name ? "is-info "
|
||||
: this.playlistName == name ? 'is-primary '
|
||||
: '') : '')
|
||||
+ "button has-text-weight-bold";
|
||||
+ (this.panel == name ? "open"
|
||||
: this.playlistName == name ? 'active' : '') : '')
|
||||
+ " button";
|
||||
},
|
||||
|
||||
/// Show/hide panel
|
||||
|
@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<div class="playlist">
|
||||
<slot name="header"></slot>
|
||||
<div class="a-playlist">
|
||||
<div class="header"><slot name="header"></slot></div>
|
||||
<ul :class="listClass">
|
||||
<li v-for="(item,index) in items" :class="itemClass" @click="!hasAction('play') && select(index)"
|
||||
:key="index">
|
||||
@ -9,7 +9,7 @@
|
||||
:data="item" :index="index" :set="set" :player="player_"
|
||||
@togglePlay="togglePlay(index)"
|
||||
:actions="actions">
|
||||
<template v-slot:extra-right="{}">
|
||||
<template v-slot:actions="{}">
|
||||
<button class="button" v-if="editable" @click.stop="remove(index,true)">
|
||||
<span class="icon is-small"><span class="fa fa-close"></span></span>
|
||||
</button>
|
||||
|
@ -1,15 +1,15 @@
|
||||
<template>
|
||||
<div class="media">
|
||||
<div class="media-left">
|
||||
<div class="a-progress m-0">
|
||||
<time class="time-now">
|
||||
<slot name="value" :value="valueDisplay" :max="max">{{ format(valueDisplay) }}</slot>
|
||||
</div>
|
||||
<div ref="bar" class="media-content" @click.stop="onClick" @mouseleave.stop="onMouseMove"
|
||||
</time>
|
||||
<div ref="bar" class="a-progress-bar-container" @click.stop="onClick" @mouseleave.stop="onMouseMove"
|
||||
@mousemove.stop="onMouseMove">
|
||||
<div :class="progressClass" :style="progressStyle"> </div>
|
||||
</div>
|
||||
<div class="media-right">
|
||||
<time class="time-total">
|
||||
<slot name="value" :value="valueDisplay" :max="max">{{ format(max) }}</slot>
|
||||
</div>
|
||||
</time>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
@ -25,7 +25,7 @@ export default {
|
||||
value: Number,
|
||||
max: Number,
|
||||
format: { type: Function, default: x => x },
|
||||
progressClass: { default: 'has-background-primary' },
|
||||
progressClass: { default: 'a-progress-bar' },
|
||||
vertical: { type: Boolean, default: false },
|
||||
},
|
||||
|
||||
|
@ -1,32 +1,23 @@
|
||||
<template>
|
||||
<div class="media sound-item">
|
||||
<div class="media-left" @click.stop="$emit('togglePlay')">
|
||||
<img class="cover is-tiny" :src="item.data.cover" v-if="item.data.cover">
|
||||
</div>
|
||||
<div class="media-content">
|
||||
<slot name="content" :player="player" :item="item" :loaded="loaded">
|
||||
<h4 class="title is-5" @click.stop="$emit('togglePlay')">
|
||||
<span class="icon is-small is-size-7 blink" v-if="playing">
|
||||
<span class="fa fa-play"></span>
|
||||
</span>
|
||||
{{ name || item.name }}
|
||||
</h4>
|
||||
<a class="subtitle is-6 is-inline-block" v-if="hasAction('page') && item.data.page_url"
|
||||
:href="item.data.page_url">
|
||||
{{ item.data.page_title }}
|
||||
</a>
|
||||
</slot>
|
||||
</div>
|
||||
<div class="media-right">
|
||||
<div :class="['a-sound-item m-0 button-group', playing && 'playing' || '']">
|
||||
<slot name="title" :player="player" :item="item" :loaded="loaded">
|
||||
<span :class="['title is-flex-grow-1', playing && 'blink' || '']" @click.stop="$emit('togglePlay')">
|
||||
<span class="icon mr-3">
|
||||
<i class="fa fa-play"></i>
|
||||
</span>
|
||||
{{ name || item.name }}
|
||||
</span>
|
||||
</slot>
|
||||
<div class="button-group actions">
|
||||
<a class="button" v-if="item.data.is_downloadable"
|
||||
:href="item.data.url" target="_blank">
|
||||
<span class="icon is-small">
|
||||
<span class="fa fa-download"></span>
|
||||
</span>
|
||||
</a>
|
||||
<button class="button" v-if="player && player.sets.pin != $parent.set" @click.stop="player.togglePin(item)">
|
||||
<button :class="['button', pinned ? 'selected' : 'not-selected']" v-if="player && player.sets.pin != $parent.set" @click.stop="player.togglePin(item)">
|
||||
<span class="icon is-small">
|
||||
<span :class="(pinned ? '' : 'has-text-grey-light ') + 'fa fa-thumbtack'"></span>
|
||||
<span class="fa fa-star"></span>
|
||||
</span>
|
||||
</button>
|
||||
<slot name="actions" :player="player" :item="item" :loaded="loaded"></slot>
|
||||
|
Reference in New Issue
Block a user