Updated color scheme and identity
This commit is contained in:
27
app/app.vue
27
app/app.vue
@@ -1,6 +1,5 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { ConfigProvider } from "radix-vue"
|
import { ConfigProvider } from "radix-vue"
|
||||||
import { cn } from "./lib/utils";
|
|
||||||
|
|
||||||
useHead({
|
useHead({
|
||||||
titleTemplate: (titleChunk) => {
|
titleTemplate: (titleChunk) => {
|
||||||
@@ -27,33 +26,17 @@ useHead({
|
|||||||
})
|
})
|
||||||
|
|
||||||
const useIdFunction = () => useId()
|
const useIdFunction = () => useId()
|
||||||
|
|
||||||
const { isSidebarOpened } = storeToRefs(useUiStore())
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<div class="h-screen">
|
<div class="h-screen">
|
||||||
<NuxtLoadingIndicator />
|
<NuxtLoadingIndicator />
|
||||||
|
|
||||||
<NuxtLayout>
|
<ConfigProvider :use-id="useIdFunction">
|
||||||
<ConfigProvider :use-id="useIdFunction">
|
<NuxtLayout>
|
||||||
<div
|
<NuxtPage />
|
||||||
class="h-full grid md:grid-cols-[auto_1fr] dark:bg-black shadow-body-light dark:shadow-body-dark transition-colors after:absolute after:transition-colors"
|
</NuxtLayout>
|
||||||
:class="cn({
|
</ConfigProvider>
|
||||||
'max-md:after:bg-transparent': isSidebarOpened,
|
|
||||||
'has-sidebar max-md:after:bg-black/20 md:after:opacity-0 md:after:pointer-events-none': isSidebarOpened
|
|
||||||
})"
|
|
||||||
>
|
|
||||||
<Sidebar />
|
|
||||||
|
|
||||||
<div
|
|
||||||
class="wrapper max-h-screen transition-all overflow-y-auto"
|
|
||||||
>
|
|
||||||
<NuxtPage />
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</ConfigProvider>
|
|
||||||
</NuxtLayout>
|
|
||||||
|
|
||||||
<ClientOnly>
|
<ClientOnly>
|
||||||
<UiToaster />
|
<UiToaster />
|
||||||
|
|||||||
@@ -116,6 +116,11 @@
|
|||||||
--color-event-white-background: var(--event-white-background);
|
--color-event-white-background: var(--event-white-background);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
::selection {
|
||||||
|
color: var(--color-background);
|
||||||
|
background: color-mix(in srgb, var(--color-primary), var(--color-foreground) 20%)
|
||||||
|
}
|
||||||
|
|
||||||
.event-button,
|
.event-button,
|
||||||
.event-popover,
|
.event-popover,
|
||||||
.event-callout,
|
.event-callout,
|
||||||
|
|||||||
@@ -2,3 +2,9 @@
|
|||||||
--text-2xs: 0.7rem;
|
--text-2xs: 0.7rem;
|
||||||
--text-2xs--line-height: 0.75rem;
|
--text-2xs--line-height: 0.75rem;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@layer utilities {
|
||||||
|
.flow > * + * {
|
||||||
|
margin-top: 1em;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@
|
|||||||
|
|
||||||
@import "./theme.css" layer(theme);
|
@import "./theme.css" layer(theme);
|
||||||
@import "./_typography.css" layer(theme);
|
@import "./_typography.css" layer(theme);
|
||||||
|
@import "./_typography.css" layer(utilities);
|
||||||
@import "./_colors.css" layer(theme);
|
@import "./_colors.css" layer(theme);
|
||||||
@import "./_colors.css" layer(utilities);
|
@import "./_colors.css" layer(utilities);
|
||||||
|
|
||||||
|
|||||||
@@ -14,16 +14,16 @@
|
|||||||
--border: hsl(214.3 31.8% 91.4%);
|
--border: hsl(214.3 31.8% 91.4%);
|
||||||
--input: hsl(214.3 31.8% 91.4%);
|
--input: hsl(214.3 31.8% 91.4%);
|
||||||
|
|
||||||
--primary: hsl(245 58% 51%);
|
--primary: rgb(101, 230, 166);
|
||||||
--primary-foreground: hsl(0 0% 100%);
|
--primary-foreground: hsl(222.2 84% 4.9%);
|
||||||
|
|
||||||
--secondary: hsl(210 50% 95%);
|
--secondary: hsl(210 50% 95%);
|
||||||
--secondary-foreground: hsl(222.2 47.4% 11.2%);
|
--secondary-foreground: hsl(222.2 84% 4.9%);
|
||||||
|
|
||||||
--accent: hsl(210 40% 96.1%);
|
--accent: hsl(11, 100%, 86%);
|
||||||
--accent-foreground: hsl(222.2 47.4% 11.2%);
|
--accent-foreground: hsl(222.2 84% 4.9%);
|
||||||
|
|
||||||
--destructive: hsl(0 84.2% 60.2%);
|
--destructive: hsl(0, 62%, 49%);
|
||||||
--destructive-foreground: hsl(210 40% 98%);
|
--destructive-foreground: hsl(210 40% 98%);
|
||||||
|
|
||||||
--success: hsl(156 72% 67%);
|
--success: hsl(156 72% 67%);
|
||||||
@@ -48,19 +48,19 @@
|
|||||||
--card: hsl(180 0 4.9%);
|
--card: hsl(180 0 4.9%);
|
||||||
--card-foreground: hsl(210 40% 98%);
|
--card-foreground: hsl(210 40% 98%);
|
||||||
|
|
||||||
--border: hsl(0, 0%, 16%);
|
--border: hsl(0, 0%, 22.5%);
|
||||||
--input: hsl(244 47% 20%);
|
--input: hsl(165, 47%, 20%);
|
||||||
|
|
||||||
--primary: hsl(245 58% 51%);
|
--primary: rgb(101, 230, 166);
|
||||||
--primary-foreground: hsl(0 0% 100%);
|
--primary-foreground: hsl(180 0 4.9%);
|
||||||
|
|
||||||
--secondary: hsl(244 47% 20%);
|
--secondary: hsl(222.2 47.4% 11.2%);
|
||||||
--secondary-foreground: hsl(210 40% 98%);
|
--secondary-foreground: hsl(210 40% 98%);
|
||||||
|
|
||||||
--accent: hsl(244 47% 20%);
|
--accent: hsl(11, 78%, 67%);
|
||||||
--accent-foreground: hsl(210 40% 98%);
|
--accent-foreground: hsl(210 40% 98%);
|
||||||
|
|
||||||
--destructive: hsl(0 62.8% 30.6%);
|
--destructive: hsl(0, 62%, 49%);
|
||||||
--destructive-foreground: hsl(210 40% 98%);
|
--destructive-foreground: hsl(210 40% 98%);
|
||||||
|
|
||||||
--success: hsl(142 72% 29%);
|
--success: hsl(142 72% 29%);
|
||||||
|
|||||||
@@ -109,7 +109,7 @@ function handleFormCancel() {
|
|||||||
name="new-calendar-name"
|
name="new-calendar-name"
|
||||||
required
|
required
|
||||||
:placeholder="$t('common.title')"
|
:placeholder="$t('common.title')"
|
||||||
class="w-full py-2 -mx-1 px-1 text-xl border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600"
|
class="w-full py-2 -mx-1 px-1 text-xl border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
@input="handleNameChange"
|
@input="handleNameChange"
|
||||||
>
|
>
|
||||||
|
|
||||||
|
|||||||
@@ -66,7 +66,7 @@ function handleCancel() {
|
|||||||
:placeholder="$t('entity.calendar.event.title')"
|
:placeholder="$t('entity.calendar.event.title')"
|
||||||
:maxlength="120"
|
:maxlength="120"
|
||||||
pattern="([A-Za-zÀ-ÖØ-öø-ÿ0-9\s\&\-\~]+){3,120}"
|
pattern="([A-Za-zÀ-ÖØ-öø-ÿ0-9\s\&\-\~]+){3,120}"
|
||||||
class="w-full -my-1 py-1 -mx-1 px-1 text-lg border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600 invalid:border-red-500"
|
class="w-full -my-1 py-1 -mx-1 px-1 text-lg border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
>
|
>
|
||||||
<div class="mt-2 mb-1 text-xs opacity-50">
|
<div class="mt-2 mb-1 text-xs opacity-50">
|
||||||
{{ t('entity.calendar.event.patterns.title') }}
|
{{ t('entity.calendar.event.patterns.title') }}
|
||||||
@@ -80,7 +80,7 @@ function handleCancel() {
|
|||||||
name="new-event-description"
|
name="new-event-description"
|
||||||
:placeholder="$t('entity.addDescription')"
|
:placeholder="$t('entity.addDescription')"
|
||||||
:maxlength="1200"
|
:maxlength="1200"
|
||||||
class="w-full -my-1 py-1 -mx-1 px-1 min-h-24 max-h-36 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600 invalid:border-red-500"
|
class="w-full -my-1 py-1 -mx-1 px-1 min-h-24 max-h-36 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
/>
|
/>
|
||||||
<div class="mt-2 mb-1 text-xs opacity-50">
|
<div class="mt-2 mb-1 text-xs opacity-50">
|
||||||
{{ t('entity.calendar.event.patterns.description') }}
|
{{ t('entity.calendar.event.patterns.description') }}
|
||||||
@@ -132,7 +132,7 @@ function handleCancel() {
|
|||||||
:placeholder="$t('entity.calendar.event.addLocation')"
|
:placeholder="$t('entity.calendar.event.addLocation')"
|
||||||
:maxlength="160"
|
:maxlength="160"
|
||||||
pattern="([A-Za-zÀ-ÖØ-öø-ÿ0-9\s\&\-\~]+){3,160}"
|
pattern="([A-Za-zÀ-ÖØ-öø-ÿ0-9\s\&\-\~]+){3,160}"
|
||||||
class="w-full -my-1 py-2 px-2 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600"
|
class="w-full -my-1 py-2 px-2 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
>
|
>
|
||||||
<div class="mt-2 mb-1 text-xs opacity-50">
|
<div class="mt-2 mb-1 text-xs opacity-50">
|
||||||
{{ t('entity.calendar.event.patterns.location') }}
|
{{ t('entity.calendar.event.patterns.location') }}
|
||||||
|
|||||||
@@ -91,7 +91,7 @@ function handleFormCancel() {
|
|||||||
name="new-calendar-name"
|
name="new-calendar-name"
|
||||||
required
|
required
|
||||||
:placeholder="$t('common.title')"
|
:placeholder="$t('common.title')"
|
||||||
class="w-full py-2 -mx-1 px-1 text-xl border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600"
|
class="w-full py-2 -mx-1 px-1 text-xl border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
@input="handleNameChange"
|
@input="handleNameChange"
|
||||||
>
|
>
|
||||||
|
|
||||||
|
|||||||
@@ -82,7 +82,7 @@ function handleCancel() {
|
|||||||
:placeholder="$t('entity.calendar.event.title')"
|
:placeholder="$t('entity.calendar.event.title')"
|
||||||
:minlength="3"
|
:minlength="3"
|
||||||
:maxlength="120"
|
:maxlength="120"
|
||||||
class="w-full -my-1 py-1 -mx-1 px-1 text-lg border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600 invalid:border-red-500"
|
class="w-full -my-1 py-1 -mx-1 px-1 text-lg border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
>
|
>
|
||||||
<div class="mt-2 mb-1 text-xs opacity-50">
|
<div class="mt-2 mb-1 text-xs opacity-50">
|
||||||
{{ t('entity.calendar.event.patterns.title') }}
|
{{ t('entity.calendar.event.patterns.title') }}
|
||||||
@@ -98,7 +98,7 @@ function handleCancel() {
|
|||||||
name="new-event-description"
|
name="new-event-description"
|
||||||
:placeholder="$t('entity.addDescription')"
|
:placeholder="$t('entity.addDescription')"
|
||||||
:maxlength="1200"
|
:maxlength="1200"
|
||||||
class="w-full -my-1 py-1 -mx-1 px-1 min-h-24 max-h-36 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600 invalid:border-red-500"
|
class="w-full -my-1 py-1 -mx-1 px-1 min-h-24 max-h-36 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
/>
|
/>
|
||||||
<div class="mt-2 mb-1 text-xs opacity-50">
|
<div class="mt-2 mb-1 text-xs opacity-50">
|
||||||
{{ t('entity.calendar.event.patterns.description') }}
|
{{ t('entity.calendar.event.patterns.description') }}
|
||||||
@@ -152,7 +152,7 @@ function handleCancel() {
|
|||||||
:placeholder="$t('entity.calendar.event.addLocation')"
|
:placeholder="$t('entity.calendar.event.addLocation')"
|
||||||
:minlength="3"
|
:minlength="3"
|
||||||
:maxlength="160"
|
:maxlength="160"
|
||||||
class="w-full -my-1 py-2 px-2 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600 invalid:border-red-500"
|
class="w-full -my-1 py-2 px-2 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
>
|
>
|
||||||
|
|
||||||
<div class="mt-2 mb-1 text-xs opacity-50">
|
<div class="mt-2 mb-1 text-xs opacity-50">
|
||||||
|
|||||||
@@ -93,10 +93,10 @@ const eventsNotDisplayed: ComputedRef<number> = computed<number>(() => eventsFo
|
|||||||
>
|
>
|
||||||
<ClientOnly>
|
<ClientOnly>
|
||||||
<span
|
<span
|
||||||
class="inline-flex size-7 md:size-8 aspect-square items-center justify-center rounded-full border-1 md:border-2 border-transparent font-bold transition-colors group-hover:border-indigo-300 dark:group-hover:border-indigo-700"
|
class="inline-flex size-7 md:size-8 aspect-square items-center justify-center rounded-full border-1 md:border-2 border-transparent font-bold transition-colors group-hover:border-primary dark:group-hover:border-primary"
|
||||||
:class="{
|
:class="{
|
||||||
'text-white bg-slate-600 dark:bg-slate-800': isDefaultDate && !isSelectedDate,
|
'bg-secondary dark:bg-slate-700': isDefaultDate && !isSelectedDate,
|
||||||
'text-white bg-indigo-500': isSelectedDate
|
'bg-primary text-primary-foreground': isSelectedDate
|
||||||
}"
|
}"
|
||||||
>
|
>
|
||||||
{{ date.day }}
|
{{ date.day }}
|
||||||
|
|||||||
@@ -41,12 +41,12 @@ const breakpoints = useBreakpoints(
|
|||||||
ref="sidebarRef"
|
ref="sidebarRef"
|
||||||
:class="cn(
|
:class="cn(
|
||||||
['md:relative md:isolate w-16 py-6 grid gap-4 grid-rows-[1fr_auto] justify-center md:transition-none'], // Base appearance
|
['md:relative md:isolate w-16 py-6 grid gap-4 grid-rows-[1fr_auto] justify-center md:transition-none'], // Base appearance
|
||||||
['after:opacity-50 after:contrast-125 dark:after:opacity-75 dark:after:contrast-175 after:-hue-rotate-60'], // After styling
|
['after:opacity-50 after:contrast-125 dark:after:opacity-75'], // After styling
|
||||||
['border-r-[1px] bg-indigo-700 dark:bg-black text-white border-r-indigo-700 dark:border-r-indigo-950 shadow-navbar-light dark:shadow-navbar-dark'], // Colours
|
['border-r-[1px] border-r-border dark:border-r-border'], // Colours
|
||||||
['max-md:justify-stretch max-md:px-4 max-md:py-4 max-md:absolute max-md:left-0 max-md:inset-0 max-md:z-50 max-md:w-40 max-md:max-w-full max-md:transition-all'], // Responsive behaviours
|
['max-md:justify-stretch max-md:px-4 max-md:py-4 max-md:absolute max-md:left-0 max-md:inset-0 max-md:z-50 max-md:w-40 max-md:max-w-full max-md:transition-all'], // Responsive behaviours
|
||||||
{
|
{
|
||||||
'max-md:-translate-x-40': !isSidebarOpened,
|
'max-md:-translate-x-40': !isSidebarOpened,
|
||||||
'max-md:-translate-x-0 shadow-navbar-dark dark:bg-slate-950': isSidebarOpened
|
'max-md:-translate-x-0': isSidebarOpened
|
||||||
}
|
}
|
||||||
)"
|
)"
|
||||||
>
|
>
|
||||||
@@ -72,11 +72,11 @@ const breakpoints = useBreakpoints(
|
|||||||
class="rounded-full max-md:hidden"
|
class="rounded-full max-md:hidden"
|
||||||
as-child
|
as-child
|
||||||
>
|
>
|
||||||
<RouterLink to="/explore">
|
<NuxtLink to="/explore">
|
||||||
<PhCompass size="24" weight="fill" />
|
<PhCompass size="24" weight="fill" />
|
||||||
</RouterLink>
|
</NuxtLink>
|
||||||
</UiButton>
|
</UiButton>
|
||||||
<RouterLink
|
<NuxtLink
|
||||||
to="/explore"
|
to="/explore"
|
||||||
class="md:hidden flex items-center gap-[.6ch] underline-offset-4 hover:underline"
|
class="md:hidden flex items-center gap-[.6ch] underline-offset-4 hover:underline"
|
||||||
>
|
>
|
||||||
@@ -85,7 +85,7 @@ const breakpoints = useBreakpoints(
|
|||||||
<span class="text-[.9em]">
|
<span class="text-[.9em]">
|
||||||
{{ $t('pages.explore.menuLabel') }}
|
{{ $t('pages.explore.menuLabel') }}
|
||||||
</span>
|
</span>
|
||||||
</RouterLink>
|
</NuxtLink>
|
||||||
</UiTooltipTrigger>
|
</UiTooltipTrigger>
|
||||||
<UiTooltipContent :side="'right'" :side-offset="6">
|
<UiTooltipContent :side="'right'" :side-offset="6">
|
||||||
<p>
|
<p>
|
||||||
@@ -96,40 +96,6 @@ const breakpoints = useBreakpoints(
|
|||||||
</UiTooltipProvider>
|
</UiTooltipProvider>
|
||||||
</li>
|
</li>
|
||||||
|
|
||||||
<li class="max-md:self-start">
|
|
||||||
<UiTooltipProvider :delay-duration="50" :disabled="!breakpoints.md.value">
|
|
||||||
<UiTooltip>
|
|
||||||
<UiTooltipTrigger as-child>
|
|
||||||
<UiButton
|
|
||||||
variant="ghost"
|
|
||||||
size="icon"
|
|
||||||
class="rounded-full max-md:hidden"
|
|
||||||
as-child
|
|
||||||
>
|
|
||||||
<RouterLink to="/about">
|
|
||||||
<PhInfo size="24" weight="fill" />
|
|
||||||
</RouterLink>
|
|
||||||
</UiButton>
|
|
||||||
<RouterLink
|
|
||||||
to="/about"
|
|
||||||
class="md:hidden flex items-center gap-[.6ch] underline-offset-4 hover:underline"
|
|
||||||
>
|
|
||||||
<PhInfo size="22" weight="fill" />
|
|
||||||
|
|
||||||
<span class="text-[.9em]">
|
|
||||||
{{ $t('pages.about.menuLabel') }}
|
|
||||||
</span>
|
|
||||||
</RouterLink>
|
|
||||||
</UiTooltipTrigger>
|
|
||||||
<UiTooltipContent :side="'right'" :side-offset="6">
|
|
||||||
<p>
|
|
||||||
{{ $t('pages.about.menuLabel') }}
|
|
||||||
</p>
|
|
||||||
</UiTooltipContent>
|
|
||||||
</UiTooltip>
|
|
||||||
</UiTooltipProvider>
|
|
||||||
</li>
|
|
||||||
|
|
||||||
<ClientOnly>
|
<ClientOnly>
|
||||||
<li v-for="(item, i) in currentMenu" :key="i">
|
<li v-for="(item, i) in currentMenu" :key="i">
|
||||||
<UiTooltipProvider :delay-duration="50">
|
<UiTooltipProvider :delay-duration="50">
|
||||||
@@ -142,9 +108,9 @@ const breakpoints = useBreakpoints(
|
|||||||
class="rounded-full"
|
class="rounded-full"
|
||||||
as-child
|
as-child
|
||||||
>
|
>
|
||||||
<RouterLink :to="item.to">
|
<NuxtLink :to="item.to">
|
||||||
<component :is="computeMenuItemIcon(item.phIcon)" size="24" :weight="item.phIconWeight || 'fill'" />
|
<component :is="computeMenuItemIcon(item.phIcon)" size="24" :weight="item.phIconWeight || 'fill'" />
|
||||||
</RouterLink>
|
</NuxtLink>
|
||||||
</UiButton>
|
</UiButton>
|
||||||
<UiButton
|
<UiButton
|
||||||
v-if="item.action"
|
v-if="item.action"
|
||||||
@@ -166,29 +132,5 @@ const breakpoints = useBreakpoints(
|
|||||||
</menu>
|
</menu>
|
||||||
|
|
||||||
<UserCTA />
|
<UserCTA />
|
||||||
|
|
||||||
<div class="sidebar-backdrop">
|
|
||||||
<NuxtImg src="/images/sidebar-min.webp" width="160" :preload="true" />
|
|
||||||
</div>
|
|
||||||
</nav>
|
</nav>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<style lang="scss" scoped>
|
|
||||||
nav {
|
|
||||||
.sidebar-backdrop {
|
|
||||||
display: block;
|
|
||||||
content: '';
|
|
||||||
position: absolute;
|
|
||||||
bottom: 0;
|
|
||||||
inset-inline: 0;
|
|
||||||
height: 25rem;
|
|
||||||
max-height: 100%;
|
|
||||||
display: grid;
|
|
||||||
align-items: end;
|
|
||||||
mask-image: linear-gradient(to top, var(--color-black) 25%, transparent 50%, transparent);
|
|
||||||
z-index: -1;
|
|
||||||
opacity: .5;
|
|
||||||
filter: saturate(200%);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
|
|||||||
@@ -59,7 +59,12 @@ function pushRoute(to: AvailableRoutes) {
|
|||||||
<UiDropdownMenu v-model:open="menuOpened">
|
<UiDropdownMenu v-model:open="menuOpened">
|
||||||
<UiDropdownMenuTrigger class="aspect-square">
|
<UiDropdownMenuTrigger class="aspect-square">
|
||||||
<TransitionGroup name="fade-group" appear>
|
<TransitionGroup name="fade-group" appear>
|
||||||
<UiAvatar v-if="user" id="user-avatar" class="ring-[.2rem] ring-indigo-700 dark:ring-neutral-900 cursor-pointer">
|
<UiAvatar
|
||||||
|
v-if="user"
|
||||||
|
id="user-avatar"
|
||||||
|
class="ring-[.2rem] ring-primary hover:bg-accent hover:ring-accent transition-all cursor-pointer"
|
||||||
|
:class="cn({ 'ring-accent bg-accent dark:bg-accent': menuOpened })"
|
||||||
|
>
|
||||||
<UiAvatarImage
|
<UiAvatarImage
|
||||||
:src="userMeta?.avatar_url"
|
:src="userMeta?.avatar_url"
|
||||||
:alt="userMeta?.full_name"
|
:alt="userMeta?.full_name"
|
||||||
@@ -69,7 +74,13 @@ function pushRoute(to: AvailableRoutes) {
|
|||||||
{{ $t('ui.sidebarMenu.avatarFallback') }}
|
{{ $t('ui.sidebarMenu.avatarFallback') }}
|
||||||
</UiAvatarFallback>
|
</UiAvatarFallback>
|
||||||
</UiAvatar>
|
</UiAvatar>
|
||||||
<UiButton v-else variant="outline" size="icon" class="ring-[.2rem] ring-indigo-700 dark:ring-neutral-900 rounded-full border-indigo-200 bg-indigo-700 dark:border-slate-300 dark:bg-neutral-950 dark:hover:bg-slate-50 dark:hover:text-slate-950 cursor-pointer">
|
<UiButton
|
||||||
|
v-else
|
||||||
|
variant="outline"
|
||||||
|
size="icon"
|
||||||
|
class="ring-[.2rem] ring-primary hover:bg-accent hover:ring-accent border-none dark:bg-background rounded-full bg-primary transition-all cursor-pointer"
|
||||||
|
:class="cn({ 'ring-accent bg-accent dark:bg-accent': menuOpened })"
|
||||||
|
>
|
||||||
<PhUserCircle size="24" />
|
<PhUserCircle size="24" />
|
||||||
</UiButton>
|
</UiButton>
|
||||||
</TransitionGroup>
|
</TransitionGroup>
|
||||||
|
|||||||
@@ -7,11 +7,11 @@ export const buttonVariants = cva(
|
|||||||
{
|
{
|
||||||
variants: {
|
variants: {
|
||||||
variant: {
|
variant: {
|
||||||
default: "bg-primary text-primary-foreground hover:bg-primary/90",
|
default: "bg-primary text-primary-foreground hover:bg-primary/70",
|
||||||
destructive: "bg-destructive text-destructive-foreground hover:bg-destructive/90",
|
destructive: "bg-destructive text-destructive-foreground hover:bg-destructive/90",
|
||||||
outline: "border border-input hover:bg-accent hover:text-accent-foreground",
|
outline: "border border-input hover:bg-primary hover:text-primary-foreground",
|
||||||
secondary: "bg-secondary text-secondary-foreground hover:bg-primary/20",
|
secondary: "bg-secondary text-secondary-foreground hover:bg-primary/20",
|
||||||
ghost: "hover:bg-accent hover:text-accent-foreground",
|
ghost: "hover:bg-primary/70 hover:text-primary-foreground",
|
||||||
link: "text-primary underline-offset-4 hover:underline"
|
link: "text-primary underline-offset-4 hover:underline"
|
||||||
},
|
},
|
||||||
size: {
|
size: {
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ const forwardedProps = useForwardProps(delegatedProps)
|
|||||||
v-bind="forwardedProps"
|
v-bind="forwardedProps"
|
||||||
:class="
|
:class="
|
||||||
cn(
|
cn(
|
||||||
'flex cursor-default select-none items-center rounded-sm px-2 py-1.5 text-sm outline-hidden focus:bg-accent data-[state=open]:bg-accent',
|
'flex cursor-default select-none items-center rounded-sm px-2 py-1.5 text-sm outline-hidden focus:bg-accent data-[state=open]:text-accent-foreground data-[state=open]:bg-accent transition-colors',
|
||||||
props.class
|
props.class
|
||||||
)
|
)
|
||||||
"
|
"
|
||||||
|
|||||||
@@ -67,7 +67,7 @@ function handleFormCancel() {
|
|||||||
name="new-world-name"
|
name="new-world-name"
|
||||||
required
|
required
|
||||||
:placeholder="$t('common.title')"
|
:placeholder="$t('common.title')"
|
||||||
class="w-full -my-1 mb-4 py-2 -mx-1 px-1 text-xl border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600"
|
class="w-full -my-1 mb-4 py-2 -mx-1 px-1 text-xl border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
@input="handleNameChange"
|
@input="handleNameChange"
|
||||||
>
|
>
|
||||||
|
|
||||||
@@ -76,7 +76,7 @@ function handleFormCancel() {
|
|||||||
v-model="worldSkeleton.description"
|
v-model="worldSkeleton.description"
|
||||||
name="new-world-description"
|
name="new-world-description"
|
||||||
:placeholder="$t('entity.addDescription')"
|
:placeholder="$t('entity.addDescription')"
|
||||||
class="w-full -my-1 py-1 -mx-1 px-1 min-h-24 max-h-36 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600"
|
class="w-full -my-1 py-1 -mx-1 px-1 min-h-24 max-h-36 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
/>
|
/>
|
||||||
|
|
||||||
<div class="-mx-1 grid gap-3">
|
<div class="-mx-1 grid gap-3">
|
||||||
|
|||||||
@@ -81,7 +81,7 @@ function handleFormCancel() {
|
|||||||
name="new-world-name"
|
name="new-world-name"
|
||||||
required
|
required
|
||||||
:placeholder="$t('common.title')"
|
:placeholder="$t('common.title')"
|
||||||
class="w-full -my-1 py-2 -mx-1 px-1 text-xl border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600"
|
class="w-full -my-1 py-2 -mx-1 px-1 text-xl border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
@input="handleNameChange"
|
@input="handleNameChange"
|
||||||
>
|
>
|
||||||
|
|
||||||
@@ -90,7 +90,7 @@ function handleFormCancel() {
|
|||||||
v-model="worldSkeleton.description"
|
v-model="worldSkeleton.description"
|
||||||
name="new-world-description"
|
name="new-world-description"
|
||||||
:placeholder="$t('entity.addDescription')"
|
:placeholder="$t('entity.addDescription')"
|
||||||
class="w-full -my-1 py-1 -mx-1 px-1 min-h-24 max-h-36 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-blue-600"
|
class="w-full -my-1 py-1 -mx-1 px-1 min-h-24 max-h-36 text-sm border-b-[1px] bg-transparent focus-visible:outline-hidden focus-visible:border-primary invalid:border-destructive"
|
||||||
/>
|
/>
|
||||||
|
|
||||||
<div class="-mx-1 grid gap-3">
|
<div class="-mx-1 grid gap-3">
|
||||||
|
|||||||
23
app/layouts/default.vue
Normal file
23
app/layouts/default.vue
Normal file
@@ -0,0 +1,23 @@
|
|||||||
|
<script lang="ts" setup>
|
||||||
|
import { cn } from '~/lib/utils';
|
||||||
|
|
||||||
|
const { isSidebarOpened } = storeToRefs(useUiStore())
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div
|
||||||
|
class="h-full grid md:grid-cols-[auto_1fr] dark:bg-black transition-colors after:absolute after:transition-colors"
|
||||||
|
:class="cn({
|
||||||
|
'max-md:after:bg-transparent': isSidebarOpened,
|
||||||
|
'has-sidebar max-md:after:bg-black/20 md:after:opacity-0 md:after:pointer-events-none': isSidebarOpened
|
||||||
|
})"
|
||||||
|
>
|
||||||
|
<Sidebar />
|
||||||
|
|
||||||
|
<div
|
||||||
|
class="wrapper max-h-screen transition-all overflow-y-auto"
|
||||||
|
>
|
||||||
|
<slot />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
7
app/layouts/public.vue
Normal file
7
app/layouts/public.vue
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
<template>
|
||||||
|
<div
|
||||||
|
class="wrapper max-h-screen h-full transition-all overflow-y-auto"
|
||||||
|
>
|
||||||
|
<slot />
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
@@ -3,6 +3,10 @@ import { PhCircleNotch } from '@phosphor-icons/vue'
|
|||||||
|
|
||||||
const { locale } = useI18n()
|
const { locale } = useI18n()
|
||||||
|
|
||||||
|
definePageMeta({
|
||||||
|
layout: "public"
|
||||||
|
})
|
||||||
|
|
||||||
const { data: page, refresh, status } = useLazyAsyncData(`about-content-${locale}`, () => {
|
const { data: page, refresh, status } = useLazyAsyncData(`about-content-${locale}`, () => {
|
||||||
return queryCollection("sections").path(`/sections/${locale.value}/legal`).first()
|
return queryCollection("sections").path(`/sections/${locale.value}/legal`).first()
|
||||||
})
|
})
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
import type { Calendar } from "@@/models/CalendarConfig";
|
import type { Calendar } from "@@/models/CalendarConfig";
|
||||||
|
|
||||||
definePageMeta({
|
definePageMeta({
|
||||||
middleware: ["reset-menu"]
|
layout: "public"
|
||||||
})
|
})
|
||||||
|
|
||||||
// const { data: availableCalendars, status: calendarStatus } = useLazyFetch<{ data: Calendar[] }>("/api/calendars/query", { key: "explore-calendars", query: { full: true } })
|
// const { data: availableCalendars, status: calendarStatus } = useLazyFetch<{ data: Calendar[] }>("/api/calendars/query", { key: "explore-calendars", query: { full: true } })
|
||||||
|
|||||||
@@ -4,12 +4,33 @@ useHead({
|
|||||||
})
|
})
|
||||||
|
|
||||||
definePageMeta({
|
definePageMeta({
|
||||||
middleware: ["reset-menu"]
|
layout: "public"
|
||||||
})
|
})
|
||||||
|
|
||||||
|
const { auth } = useSupabaseClient()
|
||||||
|
const user = useSupabaseUser()
|
||||||
|
const profileUrl: string = `${useRequestURL().origin}/my/`
|
||||||
|
|
||||||
|
async function handleGoogleLogin() {
|
||||||
|
const { error } = await auth.signInWithOAuth({
|
||||||
|
provider: "google",
|
||||||
|
options: {
|
||||||
|
queryParams: {
|
||||||
|
access_type: "offline",
|
||||||
|
prompt: "consent"
|
||||||
|
},
|
||||||
|
redirectTo: profileUrl
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
if (error) {
|
||||||
|
console.log(error.message)
|
||||||
|
}
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<main class="py-8 px-5 md:px-8">
|
<main class="h-full grid place-items-center py-8 px-5 md:px-8">
|
||||||
<Head>
|
<Head>
|
||||||
<Title>
|
<Title>
|
||||||
TTTools — {{ $t('head.title') }}
|
TTTools — {{ $t('head.title') }}
|
||||||
@@ -17,6 +38,22 @@ definePageMeta({
|
|||||||
<Meta name="description" :content="$t('head.description')" />
|
<Meta name="description" :content="$t('head.description')" />
|
||||||
</Head>
|
</Head>
|
||||||
|
|
||||||
<Heading level="h1">TTTools</Heading>
|
<div class="py-8 md:py-24 px-4">
|
||||||
|
<div class="flow text-center max-w-2xl mx-auto">
|
||||||
|
<h1 class="text-3xl md:text-5xl font-bold md:font-semibold">A home for your creativity</h1>
|
||||||
|
<p class="text-sm">Lorem ipsum, dolor sit amet consectetur adipisicing elit. Ipsam eos rem accusantium voluptates? Inventore dolorum reprehenderit quibusdam consequatur, totam iusto velit neque dolor dicta possimus cum, deleniti, saepe expedita culpa!</p>
|
||||||
|
|
||||||
|
<TransitionGroup name="fade-group" appear>
|
||||||
|
<UiButton v-if="user" as-child>
|
||||||
|
<NuxtLink to="/my">
|
||||||
|
Dashboard
|
||||||
|
</NuxtLink>
|
||||||
|
</UiButton>
|
||||||
|
<UiButton v-else @click="handleGoogleLogin">
|
||||||
|
Log in
|
||||||
|
</UiButton>
|
||||||
|
</TransitionGroup>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</main>
|
</main>
|
||||||
</template>
|
</template>
|
||||||
|
|||||||
Binary file not shown.
|
Before Width: | Height: | Size: 75 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 14 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 1.4 MiB |
Reference in New Issue
Block a user