Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
44 changes: 22 additions & 22 deletions src/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -300,9 +300,9 @@ function App() {
{/* Header */}
<header
ref={headerRef}
className="relative border-b border-green-500/50 p-4 overflow-hidden backdrop-blur-sm"
className="relative border-b border-green-500/50 p-2 lg:p-3 overflow-hidden backdrop-blur-sm"
>
<div className="max-w-2xl mx-auto flex items-center justify-between relative z-10">
<div className="max-w-7xl mx-auto flex items-center justify-between relative z-10">
<div className="flex items-center gap-4">
<div className="relative group">
<Monitor className="w-8 h-8 relative z-10" />
Expand All @@ -315,10 +315,10 @@ function App() {
rel="noopener noreferrer"
className="flex items-center gap-2 text-sm hover:text-green-400 transition-colors group"
>
<h1 className="text-2xl font-mono font-bold tracking-wider group-hover:text-green-400 transition-colors">
<h1 className="text-xl lg:text-2xl font-mono font-bold tracking-wider group-hover:text-green-400 transition-colors">
THE MATRIX ARCADE
</h1>
<p className="text-xs text-green-400 tracking-widest">
<p className="text-xs text-green-400 tracking-widest hidden sm:block">
SYSTEM v1.0.5
</p>
</a>
Expand Down Expand Up @@ -401,7 +401,7 @@ function App() {
)}

{/* Main Content */}
<main className="flex-1 overflow-hidden flex items-center justify-center">
<main className="flex-1 overflow-hidden flex items-center justify-center p-2 lg:p-4">
{/* Fullscreen Game View */}
{isPlaying && GameComponent ? (
<div className="relative w-full h-full">
Expand Down Expand Up @@ -438,7 +438,7 @@ function App() {
</button>
</div>
) : (
<div className="relative w-full md:w-10/12 lg:w-8/12 xl:w-6/12 max-w-2xl mx-auto flex flex-col justify-center py-2 px-4 lg:py-2 lg:px-4 max-h-full overflow-auto">
<div className="relative w-full max-w-2xl mx-auto flex flex-col justify-center h-full game-portal-container px-4">
{/* Matrix Rain Effect */}
<div className="absolute inset-0 opacity-20 pointer-events-none overflow-hidden">
{[...Array(50)].map((_, i) => (
Expand All @@ -460,14 +460,14 @@ function App() {
<div
ref={containerRef}
className={`
digital-container
digital-container game-portal-wrapper
${isTransitioning ? `transition-${transitionDirection}` : ''}
`}
>
{/* Game Portal */}
<div className="relative bg-gray-900 rounded-3xl p-3 lg:p-4 border-4 border-green-500 shadow-[0_0_50px_rgba(0,255,0,0.3)] max-w-xl mx-auto">
<div className="relative bg-gray-900 rounded-xl p-3 lg:p-4 border border-green-500 shadow-[0_0_20px_rgba(0,255,0,0.3)] w-full mx-auto">
{/* Game Display */}
<div className="relative aspect-[4/3] mb-3 lg:mb-4 rounded-lg overflow-hidden border-2 border-green-500 max-h-[300px] lg:max-h-[400px]">
<div className="relative aspect-[16/9] mb-2 lg:mb-3 rounded-lg overflow-hidden border border-green-500">
<AnimatePresence mode="wait">
<motion.div
key={selectedGame}
Expand All @@ -487,25 +487,25 @@ function App() {
</div>

{/* Controls */}
<div className="flex items-center justify-between gap-4">
<div className="game-controls-enhanced">
<button
onClick={handlePrevious}
className="p-2 lg:p-3 hover:bg-green-900 rounded-full transition-colors transform hover:scale-110"
className="p-1.5 lg:p-2 hover:bg-green-900 rounded-full transition-colors transform hover:scale-110"
title="Previous game"
>
<ChevronLeft className="w-8 h-8" />
<ChevronLeft className="w-6 h-6" />
</button>

<div className="flex-1 text-center">
<div className="flex items-center justify-center gap-3 mb-2">
<div className="lg:scale-110">
{games[selectedGame].icon}
</div>
<h2 className="text-xl lg:text-2xl xl:text-3xl font-mono">
<h2 className="text-lg lg:text-xl xl:text-2xl font-mono">
{games[selectedGame].title}
</h2>
</div>
<p className="text-green-400 font-mono text-sm lg:text-base mb-4 lg:mb-6">
<p className="text-green-400 font-mono text-xs lg:text-sm mb-3 lg:mb-4">
{games[selectedGame].description}
</p>
{typeof GameComponent !== 'undefined' && (
Expand Down Expand Up @@ -565,7 +565,7 @@ function App() {
}
}
}}
className="px-6 py-2 lg:px-8 lg:py-3 bg-green-500 text-black font-mono rounded-full hover:bg-green-400 transition-colors flex items-center gap-2 mx-auto transform hover:scale-105 text-base lg:text-lg"
className="px-4 py-2 lg:px-6 lg:py-2.5 bg-green-500 text-black font-mono rounded-full hover:bg-green-400 transition-colors flex items-center gap-2 mx-auto transform hover:scale-105 text-sm lg:text-base font-bold"
>
<Play className="w-4 h-4" />
{isPlaying ? 'STOP' : 'PLAY'}
Expand All @@ -575,10 +575,10 @@ function App() {

<button
onClick={handleNext}
className="p-2 lg:p-3 hover:bg-green-900 rounded-full transition-colors transform hover:scale-110"
className="p-1.5 lg:p-2 hover:bg-green-900 rounded-full transition-colors transform hover:scale-110"
title="Next game"
>
<ChevronRight className="w-8 h-8" />
<ChevronRight className="w-6 h-6" />
</button>
</div>

Expand All @@ -596,12 +596,12 @@ function App() {
{/* Enhanced Footer */}
<footer
ref={footerRef}
className="relative border-t border-green-500/50 p-4 overflow-hidden backdrop-blur-sm bottom-0 w-full"
className="relative border-t border-green-500/50 p-2 lg:p-3 overflow-hidden backdrop-blur-sm bottom-0 w-full"
>
<div className="max-w-2xl mx-auto flex items-center justify-between relative z-10">
<div className="font-mono text-sm flex items-center gap-4">
<p className="tracking-wider">THE MATRIX ARCADE v1.0.5</p>
<div className="h-4 w-px bg-green-500/30"></div>
<div className="max-w-7xl mx-auto flex items-center justify-between relative z-10">
<div className="font-mono text-xs lg:text-sm flex items-center gap-2 lg:gap-4">
<p className="tracking-wider hidden lg:block">THE MATRIX ARCADE v1.0.5</p>
<div className="h-4 w-px bg-green-500/30 hidden lg:block"></div>
<p className="text-green-400">TAKE THE RED PILL!</p>
</div>
<div className="flex items-center gap-4">
Expand Down
115 changes: 49 additions & 66 deletions src/components/games/MatrixCloud.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ const PIPE_SPEED = 3.2; // Increased from 2.5
const PIPE_SPACING = 250; // Decreased from 280
const PIPE_GAP = 150; // Decreased from 170
const GROUND_HEIGHT = 50;
const PARTICLE_COUNT = 50; // Reduced for better performance
const PARTICLE_COUNT = 30; // Optimized for better performance
const INITIAL_LIVES = 3;
const SCORE_PER_PIPE = 10;
const COMBO_INCREMENT = 0.15; // Decreased from 0.2
Expand Down Expand Up @@ -184,6 +184,9 @@ export default function MatrixCloud({ achievementManager }: MatrixCloudProps) {
const [showTutorial, setShowTutorial] = useState(true);
const [screenShake, setScreenShake] = useState({ x: 0, y: 0 });

// Cache for performance
const groundPatternRef = useRef<CanvasGradient | null>(null);

// Sound system integration
const { playSFX, playMusic, stopMusic } = useSoundSystem();

Expand Down Expand Up @@ -840,62 +843,46 @@ export default function MatrixCloud({ achievementManager }: MatrixCloudProps) {
ctx.fillStyle = 'black';
ctx.fillRect(0, 0, 800, 400);

// Draw particles with reduced effects for performance
// Draw particles with optimized rendering
ctx.font = '12px monospace';
// Only apply shadow once for all particles
ctx.shadowColor = '#00ff00';
ctx.shadowBlur = 3;
ctx.fillStyle = 'rgba(0, 255, 0, 0.5)'; // Single color for all particles

state.particles.forEach(particle => {
ctx.save();
ctx.globalAlpha = particle.opacity;
ctx.translate(particle.x, particle.y);
ctx.rotate(particle.rotation);
ctx.scale(particle.scale, particle.scale);

ctx.fillStyle = `rgba(0, 255, 0, ${particle.opacity})`;
ctx.fillText(particle.char, 0, 0);
ctx.restore();
});

// Reset shadow for other elements
ctx.shadowBlur = 0;

// Draw pipes with simpler rendering
// Draw pipes with optimized rendering
ctx.fillStyle = '#006600'; // Default pipe color

state.pipes.forEach(pipe => {
// Use solid color instead of gradient for better performance
const green = Math.floor(102 + pipe.glowIntensity * 153);
ctx.fillStyle = `rgb(0, ${green}, 0)`;

// Only apply shadow for glowing pipes
// Change color only if pipe is glowing
if (pipe.glowIntensity > 0) {
ctx.shadowColor = '#00ff00';
ctx.shadowBlur = pipe.glowIntensity * 10;
const green = Math.floor(102 + pipe.glowIntensity * 153);
ctx.fillStyle = `rgb(0, ${green}, 0)`;
} else {
ctx.fillStyle = '#006600';
}

// Top pipe
ctx.fillRect(pipe.x, 0, 50, pipe.height);
// Bottom pipe
ctx.fillRect(pipe.x, pipe.height + PIPE_GAP, 50, 400 - (pipe.height + PIPE_GAP));

// Reset shadow
ctx.shadowBlur = 0;
});

// Draw power-ups
// Draw power-ups with optimized rendering
ctx.fillStyle = '#00ff00';

state.powerUps.forEach(powerUp => {
if (powerUp.collected) return;

ctx.save();
ctx.translate(powerUp.x + 15, powerUp.y + 15);
// Use a simpler rotation based on position for performance
ctx.rotate(powerUp.x * 0.01);

// Power-up glow
ctx.shadowColor = '#00ff00';
ctx.shadowBlur = 10;
ctx.fillStyle = '#00ff00';

// Draw power-up symbol
// Draw power-up symbol without shadow for performance
switch (powerUp.type) {
case 'shield':
ctx.beginPath();
Expand Down Expand Up @@ -926,9 +913,7 @@ export default function MatrixCloud({ achievementManager }: MatrixCloudProps) {
if (state.boss && state.boss.active) {
const boss = state.boss;

// Boss glow effect
ctx.shadowColor = '#ff0000';
ctx.shadowBlur = 20;
// Remove boss shadow for performance

// Boss body based on type
ctx.save();
Expand Down Expand Up @@ -1011,14 +996,16 @@ export default function MatrixCloud({ achievementManager }: MatrixCloudProps) {
});
}

// Draw ground with pattern
const groundPattern = ctx.createLinearGradient(0, 400 - GROUND_HEIGHT, 0, 400);
groundPattern.addColorStop(0, '#004400');
groundPattern.addColorStop(1, '#003300');
ctx.fillStyle = groundPattern;
// Draw ground with cached pattern
if (!groundPatternRef.current) {
groundPatternRef.current = ctx.createLinearGradient(0, 400 - GROUND_HEIGHT, 0, 400);
groundPatternRef.current.addColorStop(0, '#004400');
groundPatternRef.current.addColorStop(1, '#003300');
}
ctx.fillStyle = groundPatternRef.current;
ctx.fillRect(0, 400 - GROUND_HEIGHT, 800, GROUND_HEIGHT);

// Draw player with effects
// Draw player without shadow for performance
ctx.fillStyle = state.activeEffects.shield ? '#00ff00' :
state.invulnerable ? '#ff0000' : '#00cc00';

Expand All @@ -1028,11 +1015,6 @@ export default function MatrixCloud({ achievementManager }: MatrixCloudProps) {
ctx.save();
ctx.translate(50, state.playerY);

// Player glow effect
ctx.shadowColor = state.activeEffects.shield ? '#00ff00' :
state.invulnerable ? '#ff0000' : '#00cc00';
ctx.shadowBlur = 10;

PLAYER_STATES[playerState].forEach((line, i) => {
ctx.fillText(line, 0, i * 10);
});
Expand Down Expand Up @@ -1110,30 +1092,31 @@ export default function MatrixCloud({ achievementManager }: MatrixCloudProps) {
}, [generateParticles, render]);

return (
<div className="w-full h-full flex flex-col items-center justify-center bg-black p-4">
<div className="relative">
<div className="w-full h-full flex flex-col items-center justify-center bg-black">
<div className="relative w-full max-w-4xl mx-auto">
<canvas
ref={canvasRef}
width={800}
height={400}
role="img"
aria-label="Matrix Cloud game canvas"
className="border-2 border-green-500 rounded-lg shadow-[0_0_20px_rgba(0,255,0,0.3)]"
className="w-full h-auto border-2 border-green-500 rounded-lg shadow-[0_0_20px_rgba(0,255,0,0.3)]"
style={{ maxHeight: '70vh' }}
onClick={jump}
/>

{/* Enhanced HUD */}
<div className="absolute top-4 left-4 flex flex-col gap-4">
<div className="flex items-center gap-2 bg-black bg-opacity-50 px-3 py-1 rounded">
<Wifi className="w-5 h-5 text-green-400" />
<div className="absolute top-4 left-4 flex flex-col gap-2 text-sm">
<div className="flex items-center gap-2 bg-black bg-opacity-70 px-2 py-1 rounded">
<Wifi className="w-4 h-4 text-green-400" />
<span>Level: {state.level}</span>
</div>
<div className="flex items-center gap-2 bg-black bg-opacity-50 px-3 py-1 rounded">
<Zap className="w-5 h-5 text-blue-400" />
<div className="flex items-center gap-2 bg-black bg-opacity-70 px-2 py-1 rounded">
<Zap className="w-4 h-4 text-blue-400" />
<span>Combo: x{state.combo.toFixed(1)}</span>
</div>
<div className="flex items-center gap-2 bg-black bg-opacity-50 px-3 py-1 rounded">
<Trophy className="w-5 h-5 text-yellow-400" />
<div className="flex items-center gap-2 bg-black bg-opacity-70 px-2 py-1 rounded">
<Trophy className="w-4 h-4 text-yellow-400" />
<span>High Score: {state.highScore}</span>
</div>
{state.inBossBattle && state.boss && (
Expand All @@ -1147,23 +1130,23 @@ export default function MatrixCloud({ achievementManager }: MatrixCloudProps) {
</div>

{/* Active Effects */}
<div className="absolute top-4 right-4 flex flex-col gap-4">
<div className="absolute top-4 right-4 flex flex-col gap-2 text-sm">
{state.activeEffects.shield && (
<div className="flex items-center gap-2 bg-black bg-opacity-50 px-3 py-1 rounded animate-pulse">
<Shield className="w-5 h-5 text-blue-400" />
<span>Shield Active</span>
<div className="flex items-center gap-2 bg-black bg-opacity-70 px-2 py-1 rounded animate-pulse">
<Shield className="w-4 h-4 text-blue-400" />
<span>Shield</span>
</div>
)}
{state.activeEffects.timeSlow && (
<div className="flex items-center gap-2 bg-black bg-opacity-50 px-3 py-1 rounded animate-pulse">
<Clock className="w-5 h-5 text-yellow-400" />
<span>Time Slow</span>
<div className="flex items-center gap-2 bg-black bg-opacity-70 px-2 py-1 rounded animate-pulse">
<Clock className="w-4 h-4 text-yellow-400" />
<span>Slow</span>
</div>
)}
{state.activeEffects.doublePoints && (
<div className="flex items-center gap-2 bg-black bg-opacity-50 px-3 py-1 rounded animate-pulse">
<Sparkles className="w-5 h-5 text-purple-400" />
<span>Double Points</span>
<div className="flex items-center gap-2 bg-black bg-opacity-70 px-2 py-1 rounded animate-pulse">
<Sparkles className="w-4 h-4 text-purple-400" />
<span>2x</span>
</div>
)}
{state.inBossBattle && (
Expand Down
Loading