0
Fork 0
mirror of https://codeberg.org/SafeTwitch/safetwitch.git synced 2024-12-21 21:03:00 -05:00

Better theme support

This commit is contained in:
dragongoose 2023-09-25 17:25:42 -04:00
parent 4d2ff16a79
commit bad5529d84
No known key found for this signature in database
GPG key ID: 01397EEC371CDAA5
24 changed files with 135 additions and 74 deletions

View file

@ -8,7 +8,7 @@ const dev = import.meta.env.DEV
</script>
<template class="h-full flex flex-row">
<div class="my-theme bg-primary">
<div class="light bg-primary">
<dev-warning v-if="dev"></dev-warning>
<navbar-item></navbar-item>

View file

@ -31,16 +31,16 @@ export default {
<div class="p-2">
<div>
<p class="font-bold text-white text-xl sm:text-base md:text-xl">
<p class="font-bold text-contrast text-xl sm:text-base md:text-xl">
{{ category.displayName }}
</p>
<p class="text-sm text-white">{{ abbreviate(category.viewers) }} viewers</p>
<p class="text-sm text-contrast">{{ abbreviate(category.viewers) }} viewers</p>
</div>
<ul class="h-8 overflow-hidden">
<li v-for="tag in category.tags" :key="tag" class="inline-flex">
<span
class="p-2.5 py-1.5 bg-surface0 rounded-md m-0.5 text-xs font-bold text-white"
class="p-2.5 py-1.5 bg-surface0 rounded-md m-0.5 text-xs font-bold text-contrast"
>{{ tag }}</span
>
</li>

View file

@ -20,10 +20,10 @@ export default {
<img :src="channelData.pfp" class="rounded-full w-20" />
<div>
<div class="inline-flex w-full justify-between">
<h1 class="text-white text-3xl font-bold">{{ channelData.username }}</h1>
<p class="text-white float-right ml-5">{{ channelData.followers }} followers</p>
<h1 class="text-contrast text-3xl font-bold">{{ channelData.username }}</h1>
<p class="text-contrast float-right ml-5">{{ channelData.followers }} followers</p>
</div>
<p class="text-white overflow-y-hidden overflow-ellipsis max-h-12">
<p class="text-contrast overflow-y-hidden overflow-ellipsis max-h-12">
{{ channelData.about }}
</p>
</div>

View file

@ -4,7 +4,7 @@ export default {}
<template>
<div
class="flex flex-col max-w-prose justify-center text-center mx-auto p-6 bg-crust rounded-lg text-white"
class="flex flex-col max-w-prose justify-center text-center mx-auto p-6 bg-crust rounded-lg text-contrast"
>
<div class="mb-6">
<h1 class="font-bold text-5xl">{{ $t('error.oops') }}</h1>

View file

@ -56,7 +56,7 @@ export default {
<button
ref="followButton"
@click="followStreamer"
class="text-white text-sm font-bold p-2 py-1 rounded-md bg-purple"
class="text-contrast text-sm font-bold p-2 py-1 rounded-md bg-purple"
>
<v-icon name="bi-heart-fill" scale="0.85"></v-icon>
<span v-if="isFollowing"> {{ $t('streamer.unfollow') }} </span>

View file

@ -10,6 +10,6 @@ export default {
<template>
<div class="m-2 mt-5 flex justify-center">
<p class="text-white font-bold">SafeTwitch {{ version}}</p>
<p class="text-contrast font-bold">SafeTwitch {{ version}}</p>
</div>
</template>

View file

@ -1,5 +1,5 @@
<template>
<div class="flex mx-auto justify-center bg-crust rounded-lg w-2/3 p-2 text-white">
<div class="flex mx-auto justify-center bg-crust rounded-lg w-2/3 p-2 text-contrast">
<div class="flex space-x-3">
<h1 class="text-4xl font-bold">{{ $t('main.searching') }}</h1>
<v-icon name="fa-circle-notch" class="animate-spin w-10 h-10"></v-icon>

View file

@ -26,14 +26,14 @@ export default {
<template>
<nav class="flex items-center justify-between flex-wrap p-4">
<div class="flex items-center flex-no-shrink text-white mr-6">
<div class="flex items-center flex-no-shrink text-contrast mr-6">
<router-link to="/">
<h1 class="font-bold text-2xl">Safe<color class="text-purple">Twitch</color></h1>
</router-link>
</div>
<search-bar class="mt-4 mr-4 hidden sm:inline-block sm:mt-0"></search-bar>
<div class="text-white hidden sm:block">
<div class="text-contrast hidden sm:block">
<a
href="https://codeberg.org/dragongoose/safetwitch"
class="mt-4 mr-4 sm:inline-block sm:mt-0"
@ -56,7 +56,7 @@ export default {
</div>
<div :class="open ? 'block' : 'hidden'" class="w-full flex-grow">
<div class="p-4 flex flex-col items-center space-y-5 text-white">
<div class="p-4 flex flex-col items-center space-y-5 text-contrast">
<search-bar></search-bar>
<ul class="inline-flex space-x-3 md:space-x-6 font-medium">
<a href="https://codeberg.org/dragongoose/safetwitch">{{ $t('nav.code') }}</a>

View file

@ -63,14 +63,14 @@ export default {
<RouterLink :to="'/' + data.login">
<img :src="data.stream.preview" class="rounded-lg rounded-b-none" />
</RouterLink>
<div class="text-white p-2 inline-flex space-x-2 w-full h-16">
<div class="text-contrast p-2 inline-flex space-x-2 w-full h-16">
<div class="inline-flex">
<div class="inline-flex">
<img :src="data.pfp" class="rounded-full mr-2" />
<div class="w-full">
<p class="font-bold w-[18rem] md:w-[22.9rem] truncate">{{ data.stream.title }}</p>
<div class="inline-flex w-full justify-between">
<p class="text-gray-300">{{ data.username }}</p>
<p class="text-neutral">{{ data.username }}</p>
<p class="self-end float-right">
<v-icon name="io-person"></v-icon> {{ abbreviate(data.stream.viewers) }}
</p>

View file

@ -164,7 +164,7 @@ export default {
</li>
<li v-for="message in getChat()" :key="messages.indexOf(message)">
<div v-if="message.type === 'PRIVMSG'" class="text-white inline-flex">
<div v-if="message.type === 'PRIVMSG'" class="text-contrast inline-flex">
<!-- CHAT MESSAGE-->
<p class="text-sm items-center">
@ -181,20 +181,20 @@ export default {
</p>
</div>
<div v-else-if="message.type === 'CLEARMSG'" class="text-white inline-flex">
<div v-else-if="message.type === 'CLEARMSG'" class="text-contrast inline-flex">
<p class="text-sm text-gray-500 italic"> {{ $t("chat.removed", { username: message.data.username }) }} </p>
</div>
<div v-else-if="message.type === 'USERNOTICE'" class="text-white inline-flex bg-pink bg-opacity-50 p-1 rounded-md">
<div v-else-if="message.type === 'USERNOTICE'" class="text-contrast inline-flex bg-pink bg-opacity-50 p-1 rounded-md">
<p> {{ $t("chat.resub", { username: message.data.username, duration : message.data.months }) }} </p>
</div>
<div v-else-if="message.type === 'CLEARCHAT'" class="text-white inline-flex p-1 rounded-md">
<div v-else-if="message.type === 'CLEARCHAT'" class="text-contrast inline-flex p-1 rounded-md">
<p v-if="!message.data.duration" class="text-sm text-gray-500 italic"> {{ $t("chat.banned", { username: message.data.username }) }} </p>
<p v-else class="text-sm text-gray-500 italic"> {{ $t("chat.timeout", { username: message.data.username, duration: message.data.duration }) }} </p>
</div>
<div v-else class="text-white">
<div v-else class="text-contrast">
{{ message }}
</div>
</li>

View file

@ -73,7 +73,7 @@ export default {
<template>
<div class="fixed top-0 bottom-0 left-0 right-0 flex w-full z-50 h-[100vh] bg-opacity-50 bg-black">
<div class="bg-crust my-auto h-min mx-auto w-[35rem] max-w-[95vw] p-5 rounded-md relative z-50 text-white">
<div class="bg-crust my-auto h-min mx-auto w-[35rem] max-w-[95vw] p-5 rounded-md relative z-50 text-contrast">
<div class="flex justify-between">
<h1 class="text-3xl font-bold">Share</h1>
<button @click="$emit('close')">

View file

@ -39,7 +39,7 @@ export default {
<ul v-if="socials" class="flex font-semibold text-md justify-start flex-wrap flex-row">
<li v-for="link in socials" :key="link.url">
<a :href="link.url" class="text-white hover:text-gray-400 mr-4 flex">
<a :href="link.url" class="text-contrast hover:text-neutral mr-4 flex">
<v-icon :name="getIconName(link.type)" class="w-6 h-6 mr-1"></v-icon>
<span>{{ link.name }}</span>
</a>

View file

@ -27,7 +27,7 @@
<div class="w-full">
<p class="font-bold text-sm truncate h-6 max-w-[255px]">{{ videoData.title }}</p>
<div class="text-xs text-gray-400">
<div class="text-xs text-neutral">
<p>{{ videoData.streamer.login }}</p>
<p>{{ videoData.game.displayName || videoData.game.name }}</p>
</div>

View file

@ -11,11 +11,11 @@ export const setLanguage = (selectedLanguage: string, i18n: any) => {
export function getDefaultSettings() {
return {
version: import.meta.env.SAFETWITCH_TAG,
audioOnly: {
name: 'audioOnly',
selected: false,
type: 'checkbox'
},
audioOnly: {
name: 'audioOnly',
selected: false,
type: 'checkbox'
},
defaultQuality: {
name: 'defaultQuality',
options: ['160p', '360p', '480p', '720p', '1080p'],
@ -57,7 +57,7 @@ export function syncUserSettings() {
if (!userSettings) return
const parsedUserSettings = JSON.parse(userSettings)
if(parsedUserSettings.version === import.meta.env.SAFETWITCH_TAG) {
if (parsedUserSettings.version === import.meta.env.SAFETWITCH_TAG) {
console.log('Settings up to date!')
return
} else {
@ -65,7 +65,7 @@ export function syncUserSettings() {
}
const synced = {...defaultSettings, ...parsedUserSettings}
const synced = { ...defaultSettings, ...parsedUserSettings }
synced.version = import.meta.env.SAFETWITCH_TAG
localStorage.setItem('settings', JSON.stringify(synced))
console.log('Migrated!')
@ -90,3 +90,50 @@ export function chatVisible() {
// is chatVisible
return !p
}
export const themeList = [
{
// name your theme anything that could be a valid css class name
// remember what you named your theme because you will use it as a class to enable the theme
name: 'dark',
// put any overrides your theme has here
// just as if you were to extend tailwind's theme like normal https://tailwindcss.com/docs/theme#extending-the-default-theme
extend: {
colors: {
"primary": '#141515',
"secondary": '#1e1f1f',
"overlay0": '#282a2a',
"overlay1": '#323434',
"surface0": '#393B3B',
"surface1": '#3F4242',
"crust": '#0C0C0C',
"purple": '#D946EF',
"red": "#980C0C",
"neutral": "#bdbdbd",
"contrast": "white",
}
}
},
{
// name your theme anything that could be a valid css class name
// remember what you named your theme because you will use it as a class to enable the theme
name: 'light',
// put any overrides your theme has here
// just as if you were to extend tailwind's theme like normal https://tailwindcss.com/docs/theme#extending-the-default-theme
extend: {
colors: {
"primary": '#ebeaea',
"secondary": '#e1e0e0',
"overlay0": '#d7d5d5',
"overlay1": '#cdcbcb',
"surface0": '#c6c4c4',
"surface1": '#c0bdbd',
"crust": '#fafafa',
"purple": '#D946EF',
"red": "#e81304",
"neutral": "gray",
"contrast": "black",
}
}
}
]

View file

@ -83,15 +83,15 @@ export default {
<div class="inline-flex space-x-4">
<img :src="data.cover" class="self-start rounded-md" />
<div>
<h1 class="font-bold text-5xl text-white">{{ data.name }}</h1>
<div class="text-contrast">
<h1 class="font-bold text-5xl">{{ data.name }}</h1>
<div class="hidden md:block">
<div>
<div class="inline-flex my-1 space-x-3">
<p class="font-bold text-white text-lg">
<p class="font-bold text-lg">
{{ $t('main.followers') }}: {{ abbreviate(data.followers) }}
</p>
<p class="font-bold text-white text-lg">
<p class="font-bold text-lg">
{{ $t('main.viewers') }}: {{ abbreviate(data.viewers) }}
</p>
</div>
@ -99,14 +99,14 @@ export default {
<ul class="mb-5">
<li v-for="tag in data.tags" :key="tag" class="inline-flex">
<span
class="text-white p-1 py-0.5 mr-1 text-sm font-bold bg-overlay1 rounded-sm"
class="p-1 py-0.5 mr-1 text-sm font-bold bg-overlay1 rounded-sm"
>{{ tag }}</span
>
</li>
</ul>
</div>
</div>
<p class="text-md text-gray-400 overflow-y-auto hidden md:block">
<p class="text-md text-neutral overflow-y-auto hidden md:block">
{{ data.description }}
</p>
</div>
@ -115,10 +115,10 @@ export default {
<div class="md:hidden">
<div>
<div class="inline-flex my-1 space-x-3">
<p class="font-bold text-white text-lg">
<p class="font-bold text-contrast text-lg">
{{ $t('main.followers') }}: {{ abbreviate(data.followers) }}
</p>
<p class="font-bold text-white text-lg">
<p class="font-bold text-contrast text-lg">
{{ $t('main.viewers') }}: {{ abbreviate(data.viewers) }}
</p>
</div>

View file

@ -93,7 +93,7 @@ export default {
class="w-full justify-center md:inline-flex space-y-4 md:space-y-0 md:space-x-4 md:p-4"
>
<div
class="flex bg-crust flex-col p-6 rounded-lg w-[99vw] md:max-w-prose md:min-w-[65ch] lg:max-w-[70rem] text-white"
class="flex bg-crust flex-col p-6 rounded-lg w-[99vw] md:max-w-prose md:min-w-[65ch] lg:max-w-[70rem] text-contrast"
>
<div class="w-full mx-auto rounded-lg mb-5">
<video-player :options="videoOptions">
@ -114,7 +114,7 @@ export default {
<router-link :to="'/' + data.streamer.login">
<h1 class="text-2xl md:text-4xl font-bold">{{ data.streamer.username }}</h1>
</router-link>
<p class="text-sm font-bold text-gray-200 self-end">
<p class="text-sm font-bold text-neutral self-end">
{{ truncate(data.title, 130) }}
</p>
</div>

View file

@ -112,12 +112,12 @@ export default {
</ul>
</div>
<div class="p-2">
<h1 class="font-bold text-5xl text-white">{{ $t('home.discover') }}</h1>
<p class="text-xl text-white">{{ $t('home.discoverDescription') }}</p>
<div class="p-2 text-contrast">
<h1 class="font-bold text-5xl">{{ $t('home.discover') }}</h1>
<p class="text-xl">{{ $t('home.discoverDescription') }}</p>
<div class="pt-5 inline-flex text-white">
<p class="mr-2 font-bold text-white">{{ $t('home.tagDescription') }}</p>
<div class="pt-5 inline-flex">
<p class="mr-2 font-bold">{{ $t('home.tagDescription') }}</p>
<div class="relative">
<label for="searchBar" class="hidden">{{ $t('main.search') }}</label>
<v-icon name="io-search-outline" class="absolute my-auto inset-y-0 left-2"></v-icon>
@ -129,7 +129,7 @@ export default {
v-model="filterTags"
@keypress="filterSearches(filterTags)"
@keyup="filterSearches(filterTags)"
class="rounded-md p-1 pl-8 text-black bg-neutral-500 placeholder:text-white"
class="rounded-md p-1 pl-8 placeholder:text-white"
/>
</div>
</div>

View file

@ -3,9 +3,9 @@ export default {}
</script>
<template>
<div class="flex flex-col items-center pt-10 font-bold text-5xl text-white">
<div class="flex flex-col items-center pt-10 font-bold text-5xl text-contrast">
<h1>{{ $t('error.oops') }}</h1>
<h1>{{ $t('error.notfound') }}</h1>
<h2 class="text-4xl">maybe go <RouterLink to="/" class="text-gray-500">home</RouterLink>?</h2>
<h2 class="text-4xl">maybe go <RouterLink to="/" class="text-contrast">home</RouterLink>?</h2>
</div>
</template>

View file

@ -3,7 +3,7 @@ export default {}
</script>
<template>
<article class="prose prose-invert bg-crust rounded-lg mx-auto p-8 pt-10 text-white">
<article class="prose prose-invert bg-crust rounded-lg mx-auto p-8 pt-10 text-contrast">
<h1>Privacy Policy</h1>
<p>
It's.... kind of empty here.

View file

@ -55,7 +55,7 @@ export default {
<div v-else-if="data" class="p-3 space-y-5">
<div v-if="data.channels.length > 0">
<h1 class="text-white font-bold text-4xl mb-2">
<h1 class="text-contrast font-bold text-4xl mb-2">
Channels related to "{{ $route.query.query }}"
</h1>
<ul class="flex overflow-x-scroll overflow-y-hidden">
@ -70,7 +70,7 @@ export default {
</div>
<div v-if="data.categories.length > 0">
<h1 class="text-white font-bold text-4xl mb-2">
<h1 class="text-contrast font-bold text-4xl mb-2">
Categories related to "{{ $route.query.query }}"
</h1>
<ul class="flex max-w-[100vw] max-h-[27rem] overflow-x-scroll overflow-y-hidden">
@ -85,7 +85,7 @@ export default {
</div>
<div v-if="data.relatedChannels.length > 0">
<h1 class="text-white font-bold text-4xl mb-2">
<h1 class="text-contrast font-bold text-4xl mb-2">
Live channels with the tag "{{ $route.query.query }}"
</h1>
<ul class="flex overflow-x-scroll space-x-5">
@ -96,7 +96,7 @@ export default {
</div>
<div v-if="data.channelsWithTag.length > 0">
<h1 class="text-white font-bold text-4xl mb-2">
<h1 class="text-contrast font-bold text-4xl mb-2">
Channels with the tag "{{ $route.query.query }}"
</h1>
<ul class="inline-flex overflow-y-hidden overflow-x-scroll max-w-[100vw] space-x-5">

View file

@ -1,5 +1,5 @@
<script lang="ts">
import { getDefaultSettings, syncUserSettings, setLanguage } from '@/settingsManager'
import { getDefaultSettings, syncUserSettings, setLanguage, themeList } from '@/settingsManager'
export default {
setup() {
@ -14,7 +14,8 @@ export default {
}
return {
settings
settings,
themeList
}
},
methods: {
@ -50,7 +51,7 @@ export default {
</script>
<template>
<div class="mx-auto w-[35rem] max-w-[95vw] p-5 py-3 bg-secondary rounded-md text-white">
<div class="mx-auto w-[35rem] max-w-[95vw] p-5 py-3 bg-secondary rounded-md text-contrast">
<h1 class="font-bold text-3xl">{{ $t("nav.settings") }}</h1>
<hr class="my-2" />
<ul class="w-full space-y-1">

View file

@ -96,7 +96,7 @@ export default {
class="w-full justify-center md:inline-flex space-y-4 md:space-y-0 md:space-x-4 md:p-4"
>
<div
class="flex bg-crust flex-col p-6 rounded-lg w-[99vw] md:max-w-prose md:min-w-[65ch] lg:max-w-[70rem] text-white"
class="flex bg-crust flex-col p-6 rounded-lg w-[99vw] md:max-w-prose md:min-w-[65ch] lg:max-w-[70rem] text-contrast"
>
<div v-if="data.isLive" class="w-full mx-auto rounded-lg mb-5">
<video-player v-if="Boolean($route.query['audio-only']) === false" :options="videoOptions"> </video-player>
@ -137,7 +137,7 @@ export default {
</a>
</div>
<div v-if="data.stream" class="w-[14rem] md:w-[17rem]">
<p class="text-sm font-bold text-gray-200 self-end">
<p class="text-sm font-bold text-neutral self-end">
{{ truncate(data.stream.title, 130) }}
</p>
</div>

View file

@ -92,7 +92,7 @@ export default {
class="w-full justify-center md:inline-flex space-y-4 md:space-y-0 md:space-x-4 md:p-4"
>
<div
class="flex bg-crust flex-col p-6 rounded-lg w-[99vw] md:max-w-prose md:min-w-[65ch] lg:max-w-[70rem] text-white"
class="flex bg-crust flex-col p-6 rounded-lg w-[99vw] md:max-w-prose md:min-w-[65ch] lg:max-w-[70rem] text-contrast"
>
<div class="w-full mx-auto rounded-lg mb-5">
<video-player :options="videoOptions" @PlayerTimeUpdate="handlePlayerTimeUpdate">
@ -113,7 +113,7 @@ export default {
<router-link :to="'/' + data.streamer.login">
<h1 class="text-2xl md:text-4xl font-bold">{{ data.streamer.username }}</h1>
</router-link>
<p class="text-sm font-bold text-gray-200 self-end">
<p class="text-sm font-bold text-neutral self-end">
{{ truncate(data.title, 130) }}
</p>
</div>

View file

@ -8,21 +8,11 @@ module.exports = {
},
plugins: [
require('tailwindcss-themer')({
defaultTheme: {
// put the default values of any config you want themed
// just as if you were to extend tailwind's theme like normal https://tailwindcss.com/docs/theme#extending-the-default-theme
extend: {
// colors is used here for demonstration purposes
colors: {
primary: 'red'
}
}
},
themes: [
{
// name your theme anything that could be a valid css class name
// remember what you named your theme because you will use it as a class to enable the theme
name: 'my-theme',
name: 'dark',
// put any overrides your theme has here
// just as if you were to extend tailwind's theme like normal https://tailwindcss.com/docs/theme#extending-the-default-theme
extend: {
@ -35,8 +25,31 @@ module.exports = {
"surface1": '#3F4242',
"crust": '#0C0C0C',
"purple": '#D946EF',
"red": "#980C0C"
"red": "#980C0C",
"neutral": "#bdbdbd",
"contrast": "white",
}
}
},
{
// name your theme anything that could be a valid css class name
// remember what you named your theme because you will use it as a class to enable the theme
name: 'light',
// put any overrides your theme has here
// just as if you were to extend tailwind's theme like normal https://tailwindcss.com/docs/theme#extending-the-default-theme
extend: {
colors: {
"primary": '#ebeaea',
"secondary": '#e1e0e0',
"overlay0": '#d7d5d5',
"overlay1": '#cdcbcb',
"surface0": '#c6c4c4',
"surface1": '#c0bdbd',
"crust": '#fafafa',
"purple": '#D946EF',
"red": "#e81304",
"neutral": "gray",
"contrast": "black",
}
}
}