light and dark mode fixed and default mode is the default unless you pick Spidey mode

This commit is contained in:
2026-06-29 19:28:35 +02:00
parent 7a722a7d7e
commit 98145f0264
5 changed files with 50 additions and 13 deletions
+31
View File
@@ -4,6 +4,37 @@
============================================================================ */
.theme-spidey {
--background: 240 18% 97%;
--foreground: 240 8% 14%;
--card: 0 0% 100%;
--card-foreground: 240 8% 14%;
--popover: 0 0% 100%;
--popover-foreground: 240 8% 14%;
--primary: 0 90% 46%;
--primary-foreground: 0 0% 100%;
--secondary: 220 75% 48%;
--secondary-foreground: 0 0% 100%;
--muted: 240 8% 92%;
--muted-foreground: 240 5% 50%;
--accent: 220 15% 90%;
--accent-foreground: 220 60% 28%;
--destructive: 0 70% 46%;
--destructive-foreground: 0 0% 100%;
--border: 240 8% 84%;
--input: 240 8% 84%;
--ring: 0 90% 46%;
--radius: 0.5rem;
--sidebar: 0 0% 99%;
--sidebar-foreground: 240 8% 14%;
--sidebar-primary: 0 90% 46%;
--sidebar-primary-foreground: 0 0% 100%;
--sidebar-accent: 220 20% 93%;
--sidebar-accent-foreground: 220 70% 28%;
--sidebar-border: 240 8% 84%;
--sidebar-ring: 0 90% 46%;
}
.dark.theme-spidey {
--background: 222.2 84% 4.9%;
--foreground: 210 40% 98%;
--card: 222.2 84% 4.9%;
+6
View File
@@ -12,6 +12,7 @@ import {
setSessionContext,
SESSION_COOKIE,
} from "@/lib/auth"
import { query } from "@/lib/db"
function jsonResponse(data: unknown, status: number) {
return new Response(JSON.stringify(data), {
@@ -114,6 +115,11 @@ export async function POST(request: NextRequest) {
true
)
await query(
`UPDATE users SET preferences = preferences || $2::jsonb WHERE id = $1`,
[dbUser.id, JSON.stringify({ website_theme: "default" })],
)
const token = await createSession(dbUser.id, dbUser.role_name)
await setSessionContext(dbUser.id, ipAddress)
+5
View File
@@ -4,6 +4,8 @@ import { useState, useEffect, useRef, Suspense } from "react"
import { useSearchParams, useRouter } from "next/navigation"
import { Eye, EyeOff, Loader2 } from "lucide-react"
const WEBSITE_THEME_KEY = "crm-website-theme"
const waves = [
{ a: 16, f: 0.011, s: 0.018, y: 0.38, fill: "rgba(27,176,206,0.18)" },
{ a: 20, f: 0.008, s: 0.013, y: 0.52, fill: "rgba(27,176,206,0.25)" },
@@ -227,6 +229,9 @@ function LoginForm() {
})
if (res.ok) {
localStorage.removeItem(WEBSITE_THEME_KEY)
const root = document.documentElement
root.className = root.className.split(" ").filter((c) => !c.startsWith("theme-")).join(" ").trim()
const redirectTo = searchParams.get("redirect") || "/dashboard"
router.push(redirectTo)
} else {
+4 -4
View File
@@ -41,12 +41,12 @@ function getStoredColorTheme(): string {
}
function applyColorTheme(theme: string) {
document.documentElement.className = document.documentElement.className
.replace(/\b(default|ocean|forest|sunset|midnight|rose|amber|violet|slate|ruby)\b/g, "")
.trim()
const colorThemes = ["default","ocean","forest","sunset","midnight","rose","amber","violet","slate","ruby"]
const classes = document.documentElement.className.split(" ").filter(c => !colorThemes.includes(c))
if (theme !== "default") {
document.documentElement.classList.add(theme)
classes.push(theme)
}
document.documentElement.className = classes.join(" ").trim()
localStorage.setItem(COLOR_THEME_KEY, theme)
}
+4 -9
View File
@@ -5,7 +5,6 @@ import { createContext, useContext, useState, useEffect, ReactNode, useCallback
const WEBSITE_THEME_KEY = "crm-website-theme"
const themeClasses: Record<string, string> = {
default: "theme-default",
spidey: "theme-spidey",
}
@@ -43,13 +42,6 @@ export function WebsiteThemeProvider({ children }: { children: ReactNode }) {
const [loading, setLoading] = useState(true)
useEffect(() => {
const stored = getStoredTheme()
if (stored) {
setWebsiteThemeState(stored)
applyWebsiteTheme(stored)
setLoading(false)
return
}
fetch("/api/settings/website-theme")
.then((res) => (res.ok ? res.json() : null))
.then((data) => {
@@ -59,7 +51,10 @@ export function WebsiteThemeProvider({ children }: { children: ReactNode }) {
applyWebsiteTheme(theme)
})
.catch(() => {
applyWebsiteTheme("default")
const stored = getStoredTheme()
const theme = stored || "default"
setWebsiteThemeState(theme)
applyWebsiteTheme(theme)
})
.finally(() => setLoading(false))
}, [])