From 1d08057dd85b3bf847162aa89a51fdedfa43f7a4 Mon Sep 17 00:00:00 2001 From: Naiyuan Qing <145280634+NevilleQingNY@users.noreply.github.com> Date: Sat, 28 Mar 2026 15:03:47 +0800 Subject: [PATCH] feat(settings): replace theme buttons with visual preview card selector Replace simple text buttons with macOS-style window preview cards for Light/Dark/System theme selection, using pure CSS miniature window mockups. Co-Authored-By: Claude Opus 4.6 (1M context) --- .../settings/_components/general-tab.tsx | 131 ++++++++++++++++-- 1 file changed, 118 insertions(+), 13 deletions(-) diff --git a/apps/web/app/(dashboard)/settings/_components/general-tab.tsx b/apps/web/app/(dashboard)/settings/_components/general-tab.tsx index 58eb9187..5efe4a19 100644 --- a/apps/web/app/(dashboard)/settings/_components/general-tab.tsx +++ b/apps/web/app/(dashboard)/settings/_components/general-tab.tsx @@ -1,13 +1,88 @@ "use client"; import { useTheme } from "next-themes"; -import { Sun, Moon, Monitor } from "lucide-react"; +import { cn } from "@/lib/utils"; + +const LIGHT_COLORS = { + titleBar: "#e8e8e8", + content: "#ffffff", + sidebar: "#f4f4f5", + bar: "#e4e4e7", + barMuted: "#d4d4d8", +}; + +const DARK_COLORS = { + titleBar: "#333338", + content: "#27272a", + sidebar: "#1e1e21", + bar: "#3f3f46", + barMuted: "#52525b", +}; + +function WindowMockup({ + variant, + className, +}: { + variant: "light" | "dark"; + className?: string; +}) { + const colors = variant === "light" ? LIGHT_COLORS : DARK_COLORS; + + return ( +
+ {/* Title bar */} +
+ + + +
+ {/* Content area */} +
+ {/* Sidebar */} +
+
+
+
+ {/* Main */} +
+
+
+
+
+
+
+ ); +} const themeOptions = [ - { value: "light", label: "Light", icon: Sun }, - { value: "dark", label: "Dark", icon: Moon }, - { value: "system", label: "System", icon: Monitor }, -] as const; + { value: "light" as const, label: "Light" }, + { value: "dark" as const, label: "Dark" }, + { value: "system" as const, label: "System" }, +]; export function AppearanceTab() { const { theme, setTheme } = useTheme(); @@ -16,21 +91,51 @@ export function AppearanceTab() {

Theme

-
+
{themeOptions.map((opt) => { const active = theme === opt.value; return ( ); })}