Light mode

This commit is contained in:
2026-03-11 23:27:19 +01:00 Verified
parent 658a8edf15
commit 3cda989390
16 changed files with 345 additions and 237 deletions
+31 -11
View File
@@ -2,23 +2,41 @@
'use client';
import { useEffect, useRef } from 'react';
import { useEffect, useRef, useState } from 'react';
import { useTheme } from 'next-themes';
interface MatrixRainProps {
color?: string;
fps?: number;
}
export default function MatrixRain({ color = '#84c0a0', fps = 15 }: MatrixRainProps) {
export default function MatrixRain({ color, fps = 15 }: MatrixRainProps) {
const canvasRef = useRef<HTMLCanvasElement>(null);
const lastWidth = useRef<number>(0);
const { resolvedTheme } = useTheme();
const [mounted, setMounted] = useState(false);
useEffect(() => {
const timer = setTimeout(() => setMounted(true), 0);
return () => clearTimeout(timer);
}, []);
useEffect(() => {
if (!mounted) return;
const canvas = canvasRef.current;
if (!canvas) return;
const ctx = canvas.getContext('2d');
if (!ctx) return;
const isLight = resolvedTheme === 'light';
// Use slate-50 (#f8fafc) for light mode, #0d1117 for dark mode
const bgColor = isLight ? '#f8fafc' : '#0d1117';
// The semi-transparent overlay that creates the fading trail effect
const fadeColor = isLight ? 'rgba(248, 250, 252, 0.2)' : 'rgba(13, 17, 23, 0.2)';
// A darker green for light mode to maintain contrast, or the default/prop color for dark mode
const textColor = color || (isLight ? '#1c2d25' : '#84c0a0');
const fontSize = 16;
let columns = 0;
let drops: number[] = [];
@@ -26,7 +44,7 @@ export default function MatrixRain({ color = '#84c0a0', fps = 15 }: MatrixRainPr
const setCanvasSize = () => {
canvas.width = window.innerWidth;
canvas.height = window.innerHeight + 120;
ctx.fillStyle = '#0d1117';
ctx.fillStyle = bgColor;
ctx.fillRect(0, 0, canvas.width, canvas.height);
};
@@ -43,13 +61,13 @@ export default function MatrixRain({ color = '#84c0a0', fps = 15 }: MatrixRainPr
initDrops();
const draw = () => {
ctx.fillStyle = 'rgba(13, 17, 23, 0.2)';
ctx.fillStyle = fadeColor;
ctx.fillRect(0, 0, canvas.width, canvas.height);
ctx.font = `bold ${fontSize}px monospace`;
for (let i = 0; i < drops.length; i++) {
const text = Math.random() > 0.5 ? '0' : '1';
ctx.fillStyle = color;
ctx.fillStyle = textColor;
ctx.fillText(text, i * fontSize, drops[i] * fontSize);
if (drops[i] * fontSize > canvas.height && Math.random() > 0.975) {
@@ -75,14 +93,16 @@ export default function MatrixRain({ color = '#84c0a0', fps = 15 }: MatrixRainPr
clearInterval(intervalId);
window.removeEventListener('resize', handleResize);
};
}, [color, fps]);
}, [color, fps, resolvedTheme, mounted]); // Re-run effect if theme changes
return (
<div className="fixed inset-0 pointer-events-none w-screen h-[110vh] bg-[#0d1117]" style={{ zIndex: -1 }}>
<canvas
ref={canvasRef}
className="absolute inset-0 w-full h-full opacity-[0.15] blur-[0.5px]"
/>
<div className="fixed inset-0 pointer-events-none w-screen h-[110vh] bg-slate-50 dark:bg-[#0d1117] transition-colors duration-300" style={{ zIndex: -1 }}>
{mounted && (
<canvas
ref={canvasRef}
className="absolute inset-0 w-full h-full opacity-[0.35] dark:opacity-[0.15] blur-[0.5px]"
/>
)}
</div>
);
}