From 03579bc6252665ee07b5d1efedb147c1471157d2 Mon Sep 17 00:00:00 2001 From: Sean O'Connor Date: Sat, 29 Nov 2025 03:08:10 -0500 Subject: [PATCH] feat: Implement database persistence and synchronization for user theme preferences --- .../settings/_components/settings-content.tsx | 916 +++++++++--------- src/app/layout.tsx | 12 +- .../providers/color-theme-provider.tsx | 68 +- src/components/providers/theme-provider.tsx | 50 +- src/server/api/routers/settings.ts | 40 + src/server/db/schema.ts | 3 + 6 files changed, 599 insertions(+), 490 deletions(-) diff --git a/src/app/dashboard/settings/_components/settings-content.tsx b/src/app/dashboard/settings/_components/settings-content.tsx index d9bcdc3..a8cb4b9 100644 --- a/src/app/dashboard/settings/_components/settings-content.tsx +++ b/src/app/dashboard/settings/_components/settings-content.tsx @@ -64,6 +64,7 @@ import { Switch } from "~/components/ui/switch"; import { Slider } from "~/components/ui/slider"; import { AppearanceSettings } from "./appearance-settings"; import { useAnimationPreferences } from "~/components/providers/animation-preferences-provider"; +import { Tabs, TabsContent, TabsList, TabsTrigger } from "~/components/ui/tabs"; export function SettingsContent() { const { data: session } = authClient.useSession(); @@ -322,57 +323,284 @@ export function SettingsContent() { ]; return ( -
- {/* Profile & Account Overview */} -
- {/* Profile Section */} - + + + General + Preferences + Data + + + +
+ {/* Profile Section */} + + + + + Profile Information + + + Update your personal account details + + + +
+
+ + setName(e.target.value)} + placeholder="Enter your full name" + /> +
+
+ + +

+ Email address cannot be changed +

+
+ +
+
+
+ + {/* Security Settings */} + + + + + Security Settings + + + Change your password and manage account security + + + +
+
+ +
+ setCurrentPassword(e.target.value)} + placeholder="Enter your current password" + /> + +
+
+ +
+ +
+ setNewPassword(e.target.value)} + placeholder="Enter your new password" + /> + +
+

+ Password must be at least 8 characters long +

+
+ +
+ +
+ setConfirmPassword(e.target.value)} + placeholder="Confirm your new password" + /> + +
+
+ + +
+
+
+
+
+ + + {/* Appearance Settings */} + - - Profile Information + + Appearance - Update your personal account details + Customize the look and feel of the application + + + + + + {/* Accessibility & Animation */} + + + + + Accessibility & Animation + + -
-
- - setName(e.target.value)} - placeholder="Enter your full name" + +
+
+ +

+ Turn this on to reduce or remove non-essential animations and + transitions. +

+
+ + setPrefersReducedMotion(Boolean(checked)) + } + aria-label="Toggle reduced motion" />
+
- - -

- Email address cannot be changed +

+ + + {prefersReducedMotion + ? "1.00x (locked)" + : `${animationSpeedMultiplier.toFixed(2)}x`} + +
+

+ Adjust global animation duration scaling. Lower values (0.25×, + 0.5×, 0.75×) slow animations; higher values (2×, 3×, 4×) speed + them up.

+
+ {/* Slider (desktop / larger screens) */} +
+ (t === 1 ? "1x" : `${t}x`)} + onValueChange={(v: number[]) => + setAnimationSpeedMultiplier(v[0] ?? 1) + } + aria-label="Animation speed multiplier" + className="mt-1" + disabled={prefersReducedMotion} + /> +
+ {/* Dropdown fallback (small screens) */} +
+ +
+
+ + + {/* Data Overview */} @@ -415,475 +643,229 @@ export function SettingsContent() {
-
- {/* Security Settings */} - - - - - Security Settings - - - Change your password and manage account security - - - -
-
- -
- setCurrentPassword(e.target.value)} - placeholder="Enter your current password" - /> + {/* Data Management */} + + + + + Data Management + + + Backup, restore, or manage your account data + + + +
+
-
-
-
- -
- setNewPassword(e.target.value)} - placeholder="Enter your new password" - /> - -
-

- Password must be at least 8 characters long -

-
- -
- -
- setConfirmPassword(e.target.value)} - placeholder="Confirm your new password" - /> - -
-
- - - -
-
- - {/* Accessibility & Animation */} - - - - - Accessibility & Animation - - - -
-
-
- -

- Turn this on to reduce or remove non-essential animations and - transitions. -

-
- - setPrefersReducedMotion(Boolean(checked)) - } - aria-label="Toggle reduced motion" - /> -
- -
-
- - - {prefersReducedMotion - ? "1.00x (locked)" - : `${animationSpeedMultiplier.toFixed(2)}x`} - -
-

- Adjust global animation duration scaling. Lower values (0.25×, - 0.5×, 0.75×) slow animations; higher values (2×, 3×, 4×) speed - them up. -

-
- {/* Slider (desktop / larger screens) */} -
- (t === 1 ? "1x" : `${t}x`)} - onValueChange={(v: number[]) => - setAnimationSpeedMultiplier(v[0] ?? 1) - } - aria-label="Animation speed multiplier" - className="mt-1" - disabled={prefersReducedMotion} - /> -
- {/* Dropdown fallback (small screens) */} -
- -
-
-
- - -
-
-
- - {/* Appearance Settings */} - - - - - Appearance - - - Customize the look and feel of the application - - - - - - - - {/* Data Management */} - - - - - Data Management - - - Backup, restore, or manage your account data - - - -
-
- - - - - - - - - Import Backup Data - - Upload your backup JSON file or paste the contents below. - This will add the data to your existing account. - - -
- {/* Import Method Selector */} -
- - -
- - {/* File Upload Method */} - {importMethod === "file" && ( -
- - -

- Select the JSON backup file you previously exported. -

-
- )} - - {/* Manual Paste Method */} - {importMethod === "paste" && ( -
- -