animations
This commit is contained in:
parent
1c5f272f33
commit
91b819e9c1
|
|
@ -0,0 +1,12 @@
|
||||||
|
{
|
||||||
|
"permissions": {
|
||||||
|
"allow": [
|
||||||
|
"Bash(npm run build:*)",
|
||||||
|
"Bash(npm install:*)",
|
||||||
|
"Bash(ls:*)",
|
||||||
|
"Bash(node scripts/optimize-images.js:*)",
|
||||||
|
"Bash(node scripts/optimize-images.cjs:*)",
|
||||||
|
"Skill(frontend-design)"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -2,22 +2,22 @@ import { motion } from 'framer-motion';
|
||||||
import { useMemo } from 'react';
|
import { useMemo } from 'react';
|
||||||
|
|
||||||
const BackgroundAnimations = () => {
|
const BackgroundAnimations = () => {
|
||||||
// Reduced particles for better performance (30 -> 12)
|
// Particles with better visibility (increased opacity and size)
|
||||||
const particles = useMemo(() => {
|
const particles = useMemo(() => {
|
||||||
return Array.from({ length: 12 }, (_, i) => ({
|
return Array.from({ length: 18 }, (_, i) => ({
|
||||||
id: i,
|
id: i,
|
||||||
x: Math.random() * 100,
|
x: Math.random() * 100,
|
||||||
y: Math.random() * 100,
|
y: Math.random() * 100,
|
||||||
size: Math.random() * 2 + 1,
|
size: Math.random() * 4 + 2, // Larger particles (2-6px instead of 1-3px)
|
||||||
duration: Math.random() * 12 + 8,
|
duration: Math.random() * 10 + 6,
|
||||||
delay: Math.random() * 4,
|
delay: Math.random() * 4,
|
||||||
opacity: Math.random() * 0.5 + 0.2,
|
opacity: Math.random() * 0.4 + 0.5, // Much higher opacity (0.5-0.9)
|
||||||
}));
|
}));
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
// Reduced circuit nodes for performance (12 -> 6)
|
// Circuit nodes for tech effect
|
||||||
const circuitNodes = useMemo(() => {
|
const circuitNodes = useMemo(() => {
|
||||||
return Array.from({ length: 6 }, (_, i) => ({
|
return Array.from({ length: 8 }, (_, i) => ({
|
||||||
id: i,
|
id: i,
|
||||||
x: Math.random() * 80 + 10,
|
x: Math.random() * 80 + 10,
|
||||||
y: Math.random() * 80 + 10,
|
y: Math.random() * 80 + 10,
|
||||||
|
|
@ -25,10 +25,10 @@ const BackgroundAnimations = () => {
|
||||||
}));
|
}));
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
// Reduced connection lines (half as many)
|
// Connection lines between nodes
|
||||||
const connectionLines = useMemo(() => {
|
const connectionLines = useMemo(() => {
|
||||||
const lines = [];
|
const lines = [];
|
||||||
for (let i = 0; i < circuitNodes.length - 1; i += 2) {
|
for (let i = 0; i < circuitNodes.length - 1; i++) {
|
||||||
if (i + 1 < circuitNodes.length) {
|
if (i + 1 < circuitNodes.length) {
|
||||||
lines.push({
|
lines.push({
|
||||||
id: i,
|
id: i,
|
||||||
|
|
@ -44,72 +44,106 @@ const BackgroundAnimations = () => {
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="absolute inset-0 overflow-hidden pointer-events-none" style={{ willChange: 'transform' }}>
|
<div className="absolute inset-0 overflow-hidden pointer-events-none" style={{ willChange: 'transform' }}>
|
||||||
{/* Simplified Static Grid Background - no animation for better performance */}
|
{/* Animated Grid Background */}
|
||||||
<div
|
<motion.div
|
||||||
className="absolute inset-0 opacity-30"
|
className="absolute inset-0"
|
||||||
style={{
|
style={{
|
||||||
backgroundImage: `
|
backgroundImage: `
|
||||||
linear-gradient(to right, rgba(51, 102, 255, 0.03) 1px, transparent 1px),
|
linear-gradient(to right, rgba(51, 102, 255, 0.08) 1px, transparent 1px),
|
||||||
linear-gradient(to bottom, rgba(51, 102, 255, 0.03) 1px, transparent 1px)
|
linear-gradient(to bottom, rgba(51, 102, 255, 0.08) 1px, transparent 1px)
|
||||||
`,
|
`,
|
||||||
backgroundSize: '80px 80px',
|
backgroundSize: '60px 60px',
|
||||||
willChange: 'transform',
|
willChange: 'transform',
|
||||||
}}
|
}}
|
||||||
|
animate={{
|
||||||
|
opacity: [0.3, 0.5, 0.3],
|
||||||
|
}}
|
||||||
|
transition={{
|
||||||
|
duration: 4,
|
||||||
|
repeat: Infinity,
|
||||||
|
ease: "easeInOut",
|
||||||
|
}}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
{/* SVG Container for Lines and Nodes - optimized */}
|
{/* SVG Container for Lines and Nodes */}
|
||||||
<svg className="absolute inset-0 w-full h-full" style={{ opacity: 0.5, willChange: 'transform' }}>
|
<svg className="absolute inset-0 w-full h-full" style={{ willChange: 'transform' }}>
|
||||||
|
|
||||||
{/* Simplified Connection Lines - static for better performance */}
|
{/* Animated Connection Lines */}
|
||||||
{connectionLines.map((line) => (
|
{connectionLines.map((line) => (
|
||||||
<line
|
<motion.line
|
||||||
key={line.id}
|
key={line.id}
|
||||||
x1={`${line.x1}%`}
|
x1={`${line.x1}%`}
|
||||||
y1={`${line.y1}%`}
|
y1={`${line.y1}%`}
|
||||||
x2={`${line.x2}%`}
|
x2={`${line.x2}%`}
|
||||||
y2={`${line.y2}%`}
|
y2={`${line.y2}%`}
|
||||||
stroke="rgba(51, 102, 255, 0.2)"
|
stroke="rgba(51, 102, 255, 0.4)"
|
||||||
strokeWidth="1"
|
strokeWidth="1.5"
|
||||||
opacity="0.4"
|
initial={{ pathLength: 0, opacity: 0 }}
|
||||||
|
animate={{ pathLength: 1, opacity: [0.3, 0.7, 0.3] }}
|
||||||
|
transition={{
|
||||||
|
pathLength: { duration: 2, delay: line.id * 0.3 },
|
||||||
|
opacity: { duration: 3, repeat: Infinity, ease: "easeInOut" },
|
||||||
|
}}
|
||||||
/>
|
/>
|
||||||
))}
|
))}
|
||||||
|
|
||||||
{/* Reduced Vertical Data Streams (8 -> 4) */}
|
{/* Vertical Data Streams */}
|
||||||
{[...Array(4)].map((_, i) => (
|
{[...Array(6)].map((_, i) => (
|
||||||
<motion.line
|
<motion.line
|
||||||
key={`vertical-${i}`}
|
key={`vertical-${i}`}
|
||||||
x1={`${15 + i * 25}%`}
|
x1={`${10 + i * 18}%`}
|
||||||
y1="0%"
|
y1="0%"
|
||||||
x2={`${15 + i * 25}%`}
|
x2={`${10 + i * 18}%`}
|
||||||
y2="100%"
|
y2="100%"
|
||||||
stroke="rgba(51, 102, 255, 0.15)"
|
stroke="rgba(51, 102, 255, 0.3)"
|
||||||
strokeWidth="1"
|
strokeWidth="1.5"
|
||||||
strokeDasharray="10 20"
|
strokeDasharray="8 16"
|
||||||
initial={{ strokeDashoffset: 0 }}
|
initial={{ strokeDashoffset: 0 }}
|
||||||
animate={{ strokeDashoffset: 100 }}
|
animate={{ strokeDashoffset: 100 }}
|
||||||
transition={{
|
transition={{
|
||||||
duration: 4,
|
duration: 3,
|
||||||
repeat: Infinity,
|
repeat: Infinity,
|
||||||
ease: "linear",
|
ease: "linear",
|
||||||
delay: i * 0.5,
|
delay: i * 0.4,
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
))}
|
))}
|
||||||
|
|
||||||
{/* Simplified Circuit Nodes - reduced animation */}
|
|
||||||
|
{/* Circuit Nodes with pulse ring */}
|
||||||
{circuitNodes.map((node) => (
|
{circuitNodes.map((node) => (
|
||||||
<g key={node.id}>
|
<g key={node.id}>
|
||||||
{/* Core node with simple pulse */}
|
{/* Pulse ring */}
|
||||||
<motion.circle
|
<motion.circle
|
||||||
cx={`${node.x}%`}
|
cx={`${node.x}%`}
|
||||||
cy={`${node.y}%`}
|
cy={`${node.y}%`}
|
||||||
r="2.5"
|
r="6"
|
||||||
fill="#3366ff"
|
fill="none"
|
||||||
|
stroke="#3366ff"
|
||||||
|
strokeWidth="1"
|
||||||
animate={{
|
animate={{
|
||||||
opacity: [0.6, 1, 0.6],
|
r: [6, 12, 6],
|
||||||
|
opacity: [0.8, 0, 0.8],
|
||||||
}}
|
}}
|
||||||
transition={{
|
transition={{
|
||||||
duration: 3,
|
duration: 2.5,
|
||||||
|
repeat: Infinity,
|
||||||
|
delay: node.pulseDelay,
|
||||||
|
ease: "easeOut",
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
{/* Core node */}
|
||||||
|
<motion.circle
|
||||||
|
cx={`${node.x}%`}
|
||||||
|
cy={`${node.y}%`}
|
||||||
|
r="4"
|
||||||
|
fill="#3366ff"
|
||||||
|
animate={{
|
||||||
|
opacity: [0.7, 1, 0.7],
|
||||||
|
r: [3, 4.5, 3],
|
||||||
|
}}
|
||||||
|
transition={{
|
||||||
|
duration: 2,
|
||||||
repeat: Infinity,
|
repeat: Infinity,
|
||||||
delay: node.pulseDelay,
|
delay: node.pulseDelay,
|
||||||
ease: "easeInOut",
|
ease: "easeInOut",
|
||||||
|
|
@ -119,7 +153,7 @@ const BackgroundAnimations = () => {
|
||||||
))}
|
))}
|
||||||
</svg>
|
</svg>
|
||||||
|
|
||||||
{/* Optimized Floating Data Particles with GPU acceleration */}
|
{/* Floating Data Particles - highly visible */}
|
||||||
{particles.map((particle) => (
|
{particles.map((particle) => (
|
||||||
<motion.div
|
<motion.div
|
||||||
key={particle.id}
|
key={particle.id}
|
||||||
|
|
@ -129,13 +163,12 @@ const BackgroundAnimations = () => {
|
||||||
height: `${particle.size}px`,
|
height: `${particle.size}px`,
|
||||||
left: `${particle.x}%`,
|
left: `${particle.x}%`,
|
||||||
top: `${particle.y}%`,
|
top: `${particle.y}%`,
|
||||||
opacity: particle.opacity,
|
boxShadow: '0 0 12px rgba(51, 102, 255, 0.9), 0 0 24px rgba(51, 102, 255, 0.5)',
|
||||||
boxShadow: '0 0 6px rgba(51, 102, 255, 0.6)',
|
|
||||||
willChange: 'transform, opacity',
|
willChange: 'transform, opacity',
|
||||||
}}
|
}}
|
||||||
animate={{
|
animate={{
|
||||||
y: [0, -600],
|
y: [0, -500],
|
||||||
opacity: [0, particle.opacity, 0],
|
opacity: [0, particle.opacity, particle.opacity, 0],
|
||||||
}}
|
}}
|
||||||
transition={{
|
transition={{
|
||||||
duration: particle.duration,
|
duration: particle.duration,
|
||||||
|
|
@ -146,24 +179,35 @@ const BackgroundAnimations = () => {
|
||||||
/>
|
/>
|
||||||
))}
|
))}
|
||||||
|
|
||||||
{/* Simplified Static Scanline Effect - no animation */}
|
|
||||||
<div
|
|
||||||
className="absolute inset-0 opacity-20 pointer-events-none"
|
{/* Scanline Effect */}
|
||||||
|
<motion.div
|
||||||
|
className="absolute inset-0 pointer-events-none"
|
||||||
style={{
|
style={{
|
||||||
background: `repeating-linear-gradient(
|
background: `repeating-linear-gradient(
|
||||||
0deg,
|
0deg,
|
||||||
transparent,
|
transparent,
|
||||||
transparent 2px,
|
transparent 2px,
|
||||||
rgba(51, 102, 255, 0.02) 2px,
|
rgba(51, 102, 255, 0.04) 2px,
|
||||||
rgba(51, 102, 255, 0.02) 4px
|
rgba(51, 102, 255, 0.04) 4px
|
||||||
)`,
|
)`,
|
||||||
}}
|
}}
|
||||||
|
animate={{
|
||||||
|
opacity: [0.3, 0.5, 0.3],
|
||||||
|
}}
|
||||||
|
transition={{
|
||||||
|
duration: 2,
|
||||||
|
repeat: Infinity,
|
||||||
|
ease: "easeInOut",
|
||||||
|
}}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
{/* Reduced Radial Glows (3 -> 2) with simpler animation */}
|
{/* Radial Glows */}
|
||||||
{[
|
{[
|
||||||
{ x: 25, y: 40 },
|
{ x: 20, y: 30, size: 300 },
|
||||||
{ x: 75, y: 60 },
|
{ x: 80, y: 70, size: 350 },
|
||||||
|
{ x: 50, y: 50, size: 400 },
|
||||||
].map((pos, i) => (
|
].map((pos, i) => (
|
||||||
<motion.div
|
<motion.div
|
||||||
key={`glow-${i}`}
|
key={`glow-${i}`}
|
||||||
|
|
@ -171,28 +215,28 @@ const BackgroundAnimations = () => {
|
||||||
style={{
|
style={{
|
||||||
left: `${pos.x}%`,
|
left: `${pos.x}%`,
|
||||||
top: `${pos.y}%`,
|
top: `${pos.y}%`,
|
||||||
width: '180px',
|
width: `${pos.size}px`,
|
||||||
height: '180px',
|
height: `${pos.size}px`,
|
||||||
background: 'radial-gradient(circle, rgba(51, 102, 255, 0.12) 0%, transparent 70%)',
|
background: 'radial-gradient(circle, rgba(51, 102, 255, 0.25) 0%, transparent 70%)',
|
||||||
transform: 'translate(-50%, -50%)',
|
transform: 'translate(-50%, -50%)',
|
||||||
willChange: 'transform',
|
willChange: 'transform',
|
||||||
}}
|
}}
|
||||||
animate={{
|
animate={{
|
||||||
scale: [1, 1.15, 1],
|
scale: [1, 1.3, 1],
|
||||||
opacity: [0.4, 0.6, 0.4],
|
opacity: [0.5, 0.8, 0.5],
|
||||||
}}
|
}}
|
||||||
transition={{
|
transition={{
|
||||||
duration: 6,
|
duration: 5,
|
||||||
repeat: Infinity,
|
repeat: Infinity,
|
||||||
delay: i * 2,
|
delay: i * 1.5,
|
||||||
ease: "easeInOut",
|
ease: "easeInOut",
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
))}
|
))}
|
||||||
|
|
||||||
{/* Static Corner Accent Glows - no blur for better performance */}
|
{/* Corner Accent Glows */}
|
||||||
<div className="absolute top-0 left-0 w-64 h-64 bg-gradient-to-br from-neon/8 to-transparent rounded-full opacity-40 pointer-events-none" />
|
<div className="absolute top-0 left-0 w-96 h-96 bg-gradient-to-br from-neon/20 to-transparent rounded-full opacity-60 pointer-events-none" />
|
||||||
<div className="absolute bottom-0 right-0 w-80 h-80 bg-gradient-to-tl from-neon/8 to-transparent rounded-full opacity-40 pointer-events-none" />
|
<div className="absolute bottom-0 right-0 w-[500px] h-[500px] bg-gradient-to-tl from-neon/20 to-transparent rounded-full opacity-60 pointer-events-none" />
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue