perf: throttle theme color picker, rewrite beams with CSS animation

ThemeTab: throttle applyThemeColors via requestAnimationFrame (1x/frame),
debounce queryClient.setQueryData 150ms. Fixes browser lag when dragging
color sliders (~60 calls/sec × 50+ CSS var writes).

BackgroundBeams: replace 20 framer-motion linearGradient JS loops with
pure CSS stroke-dashoffset animation on all 50 original Aceternity paths.
Single shared gradient, GPU-composited keyframes, zero per-frame JS.
This commit is contained in:
Fringg
2026-02-25 13:21:22 +03:00
parent a725265026
commit d019953693
2 changed files with 122 additions and 46 deletions

View File

@@ -149,24 +149,47 @@ export function ThemeTab() {
},
});
// Update a single color in the draft and apply preview instantly
// Throttle applyThemeColors to once per animation frame
const rafRef = useRef(0);
const querySyncRef = useRef(0);
const updateDraftColor = useCallback(
(key: keyof ThemeColors, value: string) => {
setDraftColors((prev) => {
const next = { ...prev, [key]: value };
applyThemeColors(next);
queryClient.setQueryData(['theme-colors'], next);
// Throttle CSS variable updates to 1x per frame
cancelAnimationFrame(rafRef.current);
rafRef.current = requestAnimationFrame(() => {
applyThemeColors(next);
});
// Debounce query cache update (triggers re-renders of other components)
clearTimeout(querySyncRef.current);
querySyncRef.current = window.setTimeout(() => {
queryClient.setQueryData(['theme-colors'], next);
}, 150);
return next;
});
},
[queryClient],
);
// Cleanup on unmount
useEffect(() => {
return () => {
cancelAnimationFrame(rafRef.current);
clearTimeout(querySyncRef.current);
};
}, []);
// Apply a full preset and auto-save to server
const applyPreset = useCallback(
(colors: Partial<ThemeColors>) => {
setDraftColors((prev) => {
const next = { ...prev, ...colors };
// Preset is a one-shot action — apply immediately (no throttle needed)
applyThemeColors(next);
queryClient.setQueryData(['theme-colors'], next);
// Auto-save preset to server so it persists across navigation