kopia lustrzana https://dev.funkwhale.audio/funkwhale/funkwhale
Merge branch 'dark-theme' into 'develop'
Dark Theme Closes #756 See merge request funkwhale/funkwhale!677environments/review-front-708-9rtl2l/deployments/1820
commit
1a52dfcc1d
|
@ -0,0 +1 @@
|
|||
Dark theme (#756)
|
|
@ -9,7 +9,7 @@
|
|||
<title>Funkwhale</title>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<body class="theme-light" id="body">
|
||||
<noscript>
|
||||
<strong>We're sorry but Funkwhale doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
|
||||
</noscript>
|
||||
|
|
|
@ -251,6 +251,14 @@ export default {
|
|||
this.$store.dispatch('instance/fetchSettings')
|
||||
this.fetchNodeInfo()
|
||||
},
|
||||
'$store.state.ui.theme': {
|
||||
immediate: true,
|
||||
handler (newValue, oldValue) {
|
||||
let oldTheme = oldValue || 'light'
|
||||
document.body.classList.remove(`theme-${oldTheme}`)
|
||||
document.body.classList.add(`theme-${newValue}`)
|
||||
},
|
||||
},
|
||||
'$store.state.auth.authenticated' (newValue) {
|
||||
if (!newValue) {
|
||||
this.disconnect()
|
||||
|
|
|
@ -33,6 +33,14 @@
|
|||
<a href="https://funkwhale.audio/apps" class="item" target="_blank"><translate translate-context="Footer/*/List item.Link">Mobile and desktop apps</translate></a>
|
||||
<div role="button" class="item" @click="$emit('show:shortcuts-modal')"><translate translate-context="*/*/*/Noun">Keyboard shortcuts</translate></div>
|
||||
</div>
|
||||
<div class="ui form">
|
||||
<div class="ui field">
|
||||
<label><translate translate-context="Footer/Settings/Dropdown.Label/Short, Verb">Change theme</translate></label>
|
||||
<select class="ui dropdown" :value="$store.state.ui.theme" @change="$store.commit('ui/theme', $event.target.value)">
|
||||
<option v-for="theme in themes" :key="theme.key" :value="theme.key">{{ theme.name }}</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
<section class="four wide column">
|
||||
<h4 v-translate translate-context="Footer/*/Link" class="ui header">Getting help</h4>
|
||||
|
@ -76,15 +84,18 @@ export default {
|
|||
parser.href = url
|
||||
return parser.hostname
|
||||
},
|
||||
themes () {
|
||||
return [
|
||||
{
|
||||
name: this.$pgettext('Footer/Settings/Dropdown.Label/Theme name', 'Light'),
|
||||
key: 'light'
|
||||
},
|
||||
{
|
||||
name: this.$pgettext('Footer/Settings/Dropdown.Label/Theme name', 'Dark'),
|
||||
key: 'dark'
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
<style scoped>
|
||||
footer p {
|
||||
color: grey;
|
||||
}
|
||||
|
||||
footer#footer div.item:hover {
|
||||
color: rgba(0, 0, 0, 0.87);
|
||||
}
|
||||
</style>
|
||||
|
|
|
@ -126,7 +126,4 @@ export default {
|
|||
.read > span {
|
||||
cursor: pointer;
|
||||
}
|
||||
.disabled-row {
|
||||
color: rgba(40, 40, 40, 0.3);
|
||||
}
|
||||
</style>
|
||||
|
|
|
@ -59,12 +59,10 @@ export default {
|
|||
|
||||
<!-- Add "scoped" attribute to limit CSS to this component only -->
|
||||
<style>
|
||||
|
||||
.playlist.card .header .ellipsis.vertical.large.grey {
|
||||
font-size: 1.2em;
|
||||
margin-right: 0;
|
||||
}
|
||||
|
||||
</style>
|
||||
<style scoped>
|
||||
.card .header {
|
||||
|
@ -72,8 +70,7 @@ export default {
|
|||
}
|
||||
|
||||
.attached.button {
|
||||
background-color: rgb(243, 244, 245);
|
||||
background-size: 25% ;
|
||||
background-size: 25%;
|
||||
background-repeat: no-repeat;
|
||||
background-origin: border-box;
|
||||
background-position: 0 0, 33.33% 0, 66.67% 0, 100% 0;
|
||||
|
@ -82,5 +79,4 @@ export default {
|
|||
font-size: 4em;
|
||||
box-shadow: 0px 0px 0px 1px rgba(34, 36, 38, 0.15) inset !important;
|
||||
}
|
||||
|
||||
</style>
|
||||
|
|
|
@ -40,7 +40,7 @@ export default new Vuex.Store({
|
|||
}),
|
||||
createPersistedState({
|
||||
key: 'ui',
|
||||
paths: ['ui.currentLanguage', 'ui.momentLocale']
|
||||
paths: ['ui.currentLanguage', 'ui.momentLocale', 'ui.theme']
|
||||
}),
|
||||
createPersistedState({
|
||||
key: 'radios',
|
||||
|
|
|
@ -10,6 +10,7 @@ export default {
|
|||
maxMessages: 100,
|
||||
messageDisplayDuration: 10000,
|
||||
messages: [],
|
||||
theme: 'light',
|
||||
notifications: {
|
||||
inbox: 0,
|
||||
pendingReviewEdits: 0,
|
||||
|
@ -39,6 +40,9 @@ export default {
|
|||
computeLastDate: (state) => {
|
||||
state.lastDate = new Date()
|
||||
},
|
||||
theme: (state, value) => {
|
||||
state.theme = value
|
||||
},
|
||||
addMessage (state, message) {
|
||||
state.messages.push(message)
|
||||
if (state.messages.length > state.maxMessages) {
|
||||
|
|
|
@ -10,6 +10,10 @@
|
|||
Import this file into your LESS project to use Semantic UI without build tools
|
||||
*/
|
||||
|
||||
// Those semantic-ui-css/*.scss don't exist in the package, but we create them
|
||||
// via scripts/link-scss-files.sh on postinstall, so we can include theme
|
||||
// under a class namespace
|
||||
|
||||
/* Global */
|
||||
@import "~semantic-ui-css/components/reset.css";
|
||||
// we use our custom site css here to avoid loading google font
|
||||
|
@ -96,6 +100,7 @@ body {
|
|||
#app > main, #app > .main {
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
.instance-chooser {
|
||||
margin-top: 2em;
|
||||
}
|
||||
|
@ -126,14 +131,10 @@ body {
|
|||
margin-left: 0;
|
||||
margin-right: 0;
|
||||
border: none;
|
||||
box-shadow: inset 0px -2px 0px 0px rgba(34, 36, 38, 0.15);
|
||||
.ui.item {
|
||||
border: none;
|
||||
border-bottom-style: none;
|
||||
margin-bottom: 0px;
|
||||
&.active {
|
||||
box-shadow: inset 0px -2px 0px 0px #000;
|
||||
}
|
||||
}
|
||||
@include media(">tablet") {
|
||||
padding: 0 2.5rem;
|
||||
|
@ -148,7 +149,6 @@ body {
|
|||
@include media(">widedesktop") {
|
||||
left: $widedesktop-sidebar-width;
|
||||
}
|
||||
background-color: white;
|
||||
.item {
|
||||
padding-top: 1.5em;
|
||||
padding-bottom: 1.5em;
|
||||
|
@ -208,9 +208,6 @@ body {
|
|||
}
|
||||
}
|
||||
|
||||
.discrete {
|
||||
color: rgba(0, 0, 0, 0.87);
|
||||
}
|
||||
.link {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
@ -355,3 +352,8 @@ input + .help {
|
|||
.table td .ui.dropdown {
|
||||
min-width: 150px;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@import "./themes/_light.scss";
|
||||
@import "./themes/_dark.scss";
|
||||
|
|
|
@ -0,0 +1,222 @@
|
|||
$background-color: rgb(43, 58, 66);
|
||||
$button-hover-color: rgb(33, 48, 56);
|
||||
$light-background-color: rgb(51, 71, 82);
|
||||
$input-background-color: rgb(189, 211, 222);
|
||||
$loading-background-color: rgba(43, 58, 66, 0.9);
|
||||
$text-color: rgb(223, 235, 240);
|
||||
$discrete-text-color: rgba(223, 235, 240, 0.904);
|
||||
$border-color: rgb(63, 88, 102);
|
||||
$light-shadow-color: rgba(223, 235, 240, 0.15);
|
||||
$shadow-color: rgba(63, 102, 97, 0.95);
|
||||
$box-shadow: 0px 1px 3px 0px rgba(63, 88, 102, 0.95), 0px 0px 0px 1px rgba(63, 88, 102, 0.98);
|
||||
$link-color: rgb(255, 144, 0);
|
||||
|
||||
.theme-dark {
|
||||
background-color: $background-color;
|
||||
.ui.labeled.input {
|
||||
input, .label {
|
||||
background-color: $input-background-color;
|
||||
&::placeholder {
|
||||
color: $light-background-color;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
.ui.statistics .statistic {
|
||||
> .label, > .value {
|
||||
color: $text-color;
|
||||
}
|
||||
}
|
||||
.ui.link.list.list .active.item, .ui.link.list.list .active.item a:not(.ui) {
|
||||
color: inherit;
|
||||
}
|
||||
.ui.form textarea, .ui.form select, .ui.selection.dropdown, .ui.dropdown.selected, .ui.dropdown .menu .selected.item, .ui.form input:not([type]), .ui.form input[type="date"], .ui.form input[type="datetime-local"], .ui.form input[type="email"], .ui.form input[type="number"], .ui.form input[type="password"], .ui.form input[type="search"], .ui.form input[type="tel"], .ui.form input[type="time"], .ui.form input[type="text"], .ui.form input[type="file"], .ui.form input[type="url"] {
|
||||
background-color: $input-background-color;
|
||||
&::placeholder {
|
||||
color: $light-background-color;
|
||||
|
||||
}
|
||||
}
|
||||
.ui.dropdown .menu .item:hover {
|
||||
background-color: $light-background-color;
|
||||
color: $text-color;
|
||||
|
||||
}
|
||||
.main.pusher > .ui.secondary.menu {
|
||||
background-color: $background-color;
|
||||
box-shadow: inset 0px -2px 0px 0px $light-background-color;
|
||||
.ui.item {
|
||||
color: $text-color;
|
||||
&.active {
|
||||
box-shadow: inset 0px -2px 0px 0px $shadow-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
.ui.modal {
|
||||
> .header, > .content, > .actions {
|
||||
background-color: $background-color;
|
||||
}
|
||||
> .header {
|
||||
border-bottom: 1px solid $border-color;
|
||||
}
|
||||
|
||||
> .actions {
|
||||
border-top: 1px solid $border-color;
|
||||
}
|
||||
}
|
||||
main, .main, footer, .modal {
|
||||
|
||||
.ui.menu {
|
||||
background-color: $light-background-color;
|
||||
.item {
|
||||
|
||||
color: $text-color;
|
||||
}
|
||||
}
|
||||
.ui.secondary.menu .dropdown.item:hover, .ui.secondary.menu .link.item:hover, .ui.secondary.menu a.item:hover {
|
||||
background: $background-color;
|
||||
color: $text-color;
|
||||
}
|
||||
.header, .ui.form .field > label, .sub.header {
|
||||
color: $text-color;
|
||||
}
|
||||
.ui.attached.header {
|
||||
background-color: transparent;
|
||||
}
|
||||
.ui.toggle.checkbox input:checked ~ .box, .ui.toggle.checkbox input:checked ~ label {
|
||||
color: $text-color !important;
|
||||
}
|
||||
.ui.toggle.checkbox .box::before, .ui.toggle.checkbox label::before {
|
||||
background-color: $light-background-color;
|
||||
}
|
||||
a:not(.ui):not(.discrete) {
|
||||
color: $link-color;
|
||||
}
|
||||
.ui.segment:not(.basic) {
|
||||
background-color: $light-background-color;
|
||||
}
|
||||
.ui.list, .ui.dropdown {
|
||||
.item, div.item, a.item, .button.item {
|
||||
background-color: $background-color;
|
||||
color: $discrete-text-color;
|
||||
}
|
||||
.selected.item:not(:hover) {
|
||||
color: $background-color;
|
||||
}
|
||||
}
|
||||
.ui.divided.items > .item:not(:first-child) {
|
||||
border-top: 1px solid $border-color;
|
||||
}
|
||||
.ui.items {
|
||||
.extra {
|
||||
color: $discrete-text-color;
|
||||
}
|
||||
}
|
||||
label, .toggle label {
|
||||
color: $text-color !important;
|
||||
}
|
||||
&, .main.pusher, .ui.vertical.segment {
|
||||
color: $text-color;
|
||||
background-color: $background-color;
|
||||
}
|
||||
|
||||
.discrete {
|
||||
color: $discrete-text-color;
|
||||
}
|
||||
|
||||
.ui.table thead th, .ui.table {
|
||||
color: $text-color;
|
||||
}
|
||||
.ui.divider:not(.vertical):not(.horizontal) {
|
||||
border-top: 1px solid $border-color;
|
||||
border-bottom: 1px solid $border-color;
|
||||
}
|
||||
.ui.cards > .card, .ui.card {
|
||||
color: $text-color;
|
||||
background-color: $background-color;
|
||||
box-shadow: $box-shadow;
|
||||
.content, .header, .description {
|
||||
color: $text-color;
|
||||
}
|
||||
.extra, .meta {
|
||||
color: $discrete-text-color;
|
||||
}
|
||||
}
|
||||
.playlist.card {
|
||||
.attached.button {
|
||||
background-color: $light-background-color;
|
||||
}
|
||||
}
|
||||
|
||||
// buttons
|
||||
[class='ui button ui button'], [class='ui button'], [class='ui icon button'], [class='ui fluid button'], [class='ui cancel button'] {
|
||||
background-color: $light-background-color;
|
||||
color: $text-color;
|
||||
&:hover {
|
||||
background-color: $button-hover-color;
|
||||
|
||||
}
|
||||
}
|
||||
.ui.buttons > .ui.button:not(.basic):not(.inverted), .ui.buttons:not(.basic):not(.inverted) > .button {
|
||||
box-shadow: 0px 0px 0px 1px $light-shadow-color inset;
|
||||
|
||||
}
|
||||
.ui.basic.buttons:not(:hover):not(.green):not(.orange):not(.yellow):not(.red) .button, .ui.basic.button {
|
||||
box-shadow: 0px 0px 0px 1px $text-color inset;
|
||||
&:not(:hover):not(.green):not(.orange):not(.yellow):not(.red) {
|
||||
color: $text-color !important;
|
||||
}
|
||||
}
|
||||
.ui.basic.buttons .button, .ui.basic.button {
|
||||
&:hover {
|
||||
color: $text-color !important;
|
||||
}
|
||||
|
||||
}
|
||||
.ui.basic.buttons:not(.green):not(.orange):not(.yellow):not(.red) .button:hover, .ui.basic.button:not(.green):not(.orange):not(.yellow):not(.red):hover, .ui.basic.button:not(.green):not(.orange):not(.yellow):not(.red):active, .ui.basic.button:not(.green):not(.orange):not(.yellow):not(.red):focus {
|
||||
color: $background-color !important;
|
||||
}
|
||||
// loading /dimmers
|
||||
.ui.loading.form::before {
|
||||
background-color: $loading-background-color;
|
||||
}
|
||||
.ui.inverted.dimmer {
|
||||
background-color: $loading-background-color;
|
||||
}
|
||||
// table
|
||||
.ui.basic.table tbody tr, .ui.table tr td {
|
||||
border-bottom: 1px solid $border-color;
|
||||
}
|
||||
.ui.table thead th {
|
||||
border-bottom: 1px solid $border-color;
|
||||
}
|
||||
.ui.table {
|
||||
&:not(.basic) {
|
||||
&, thead th {
|
||||
background-color: $light-background-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.ui.link.list.list a.item:hover, .ui.link.list.list .item a:not(.ui):not(.button):hover {
|
||||
color: $link-color;
|
||||
}
|
||||
[data-tooltip]::after {
|
||||
background-color: $light-background-color;
|
||||
color: $text-color;
|
||||
}
|
||||
.ui.progress > .label {
|
||||
color: $text-color;
|
||||
|
||||
}
|
||||
i.grey.icon {
|
||||
color: $text-color !important;
|
||||
}
|
||||
input {
|
||||
&::selection, &::-moz-selection {
|
||||
background: $background-color;
|
||||
color: $text-color;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,35 @@
|
|||
|
||||
|
||||
.theme-light {
|
||||
|
||||
.main.pusher > .ui.secondary.menu {
|
||||
box-shadow: inset 0px -2px 0px 0px rgba(34, 36, 38, 0.15);
|
||||
background-color: white;
|
||||
.ui.item {
|
||||
&.active {
|
||||
box-shadow: inset 0px -2px 0px 0px #000;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.discrete {
|
||||
color: rgba(0, 0, 0, 0.87);
|
||||
}
|
||||
.playlist.card {
|
||||
.attached.button {
|
||||
background-color: rgb(243, 244, 245);
|
||||
}
|
||||
}
|
||||
|
||||
.disabled-row {
|
||||
color: rgba(40, 40, 40, 0.3);
|
||||
}
|
||||
footer p {
|
||||
color: grey;
|
||||
}
|
||||
|
||||
footer#footer div.item:hover {
|
||||
color: rgba(0, 0, 0, 0.87);
|
||||
}
|
||||
|
||||
}
|
Ładowanie…
Reference in New Issue