SandGame/README.md

7.5 KiB
Raw Permalink Blame History

Falling Sand Simulation 🧱✨

A high-performance, modular falling sand physics sandbox built in vanilla JavaScript and HTML5 Canvas. Experience realistic particulate physics, fluid dynamics, thermodynamics, combustion, and chemical reactions running at a silky-smooth 60+ FPS.


⚡ Performance & Engine Architecture

  • Direct 32-Bit Pixel Blitter (Uint32Array / ImageData): Replaces traditional Canvas 2D fillRect / arc draw calls with direct memory writes into a 32-bit RGBA pixel buffer on an offscreen buffer canvas, delivering a 50x–100x rendering speedup that comfortably handles hundreds of thousands of active particles.
  • Rapid Fluid Dispersion: Liquids (water, acid, oil) dynamically disperse up to customizable multi-cell horizontal steps per frame, eliminating gelatinous stacking and delivering realistic splashing and surface leveling.
  • Oil & Water Emulsion & Separation: Water and oil mix dynamically with diagonal and horizontal swapping before buoyantly separating out according to density.
  • Lava & Rock Sinking: Dense molten lava plunges into water, boiling it into rising steam, and solidifies into stone that naturally sinks through liquid to the bottom of the pool.
  • Monotonic Frame Counter & Alternating Sweep: Eliminates the legacy full-grid updated = false pass. Cells track lastUpdated = currentFrame. The simulation loop alternates horizontal scan direction (left-to-right vs. right-to-left) every frame to eliminate asymmetric pile-up bias in liquids and sand.
  • Zero-Allocation Hot Loop: All neighbor evaluations, directional offsets, and particle physics run with zero heap allocations or closures, preventing garbage collection pauses and stuttering.
  • Bresenham Stroke Interpolation: Uses Bresenham's line algorithm between consecutive cursor samples to ensure smooth, gapless lines even when drawing at high speeds.
  • Non-Destructive Canvas Resizing: Resizing the window or changing device orientation preserves existing particles on the canvas rather than wiping the simulation.

🧪 Element & Reaction Ecosystem

Element Category Behavior & Unique Reactions
Sand Solid Granular physics; forms realistic dunes; sinks through liquids.
Dirt Solid Rich earthen soil; supports plant and grass roots; displaceable by explosions.
Rock Solid Heavy barrier; holds back blasts; naturally sinks through liquids to form riverbeds.
Wood Solid Rigid structural block; flammable when exposed to fire or lava.
Ice Solid Crystalline cold block; slowly freezes touching water; melts near heat/fire/lava.
Water Liquid Flows rapidly; mixes with and separates from oil; turns lava into rock; boils into steam.
Lava Liquid Heavy molten magma; plunges into water boiling it into steam; cools into solid rock.
Oil Liquid Viscous flammable liquid; mixes with water and then floats to the surface; catches fire intensely.
Acid Liquid Corrosive fluid; fast dispersion; sinks through lighter liquids; dissolves organics, metals, and earth.
Plant Organics Grows upwards towards light; absorbs water; turns into wood under vertical load.
Grass Organics Colonizes surface dirt and sand; sprouts blades; accelerates with moisture.
Fire Gas / Energy Dynamic temperature shading (yellow \rightarrow orange \rightarrow red); ignites flammables; spawns smoke.
Steam Gas Rises through atmosphere and liquids; escapes into the sky or condenses back into water.
Smoke Gas Produced by fires, explosions, and burning oil; drifts with air turbulence and dissipates.
TNT Energetic Detonates from fire, lava, or acid; clusters into unified blast waves launching particles kinetically.
Eraser Tool Clears cells within brush radius; also accessible via right-click drag.

🎮 Controls & Shortcuts

Action Control
Draw Element Left Click + Drag / Touch
Erase Right Click + Drag or select Eraser
Brush Size Mouse Wheel or [ / ] or Drawer Slider
Pause / Play Spacebar or Pause button (⏸ / ▶)
Single Frame Step S or . (Period) or Step button (⏭)
Clear Canvas Clear button in Elements drawer

⚙️ Configuration & Customization

All simulation and material parameters can be tuned in real time via the Settings ⚙️ drawer:

  • Time & Global: Simulation speed (0–20), gravity (-1.0 to 2.0), air drag (0.1 to 1.0).
  • Explosive: Blast force, blast reach, plus independent destruction toggles for Rock, Wood, Dirt, Sand, Plant, Grass, Water, Acid, Ice, Lava, and Oil.
  • Acid: Dissolve rate, sink rate, spread speed, explode TNT toggle, plus independent dissolve toggles for Rock, Wood, Dirt, Sand, Plant, Grass, Water (infection), Ice, and Oil.
  • Water: Flow rate and horizontal spread speed (dispersion).
  • Lava: Flow rate, spread speed, cooling rate, and water sink rate.
  • Oil: Flow rate, spread speed, burn rate, water sink rate, and oil float rate.
  • Ice: Melt rate and freeze rate.
  • Fire, Steam & Smoke: Fire decay rate, condensation rate, and smoke dissipation rate.
  • Plant & Grass: Growth rate, woodification rate, and burn rate.
  • Visuals: Switch between blocky, fuzzy (filtered bloom), or bloby rendering, and toggle multi-tone grain color noise.
  • Settings are automatically saved to localStorage and can be restored using Reset to Defaults.

📂 Project Structure

├── index.html        # HTML5 entrypoint with drawers and canvas
├── index.css         # Glassmorphic dark UI design and responsive styles
├── index.js          # Main initialization loop, event loop, and input wiring
├── config.js         # Config defaults, settings persistence, and schema
├── state.js          # Grid buffers, canvas dimensions, brush, and frame counter
├── actions.js        # Atomic grid operations (move, swap) with frame tagging
├── renderer.js       # Fast 32-bit Uint32Array blitter with cursor overlay
├── physics.js        # Simulation loop dispatcher and particle generation
├── dirt.js           # Granular sand and soil physics with liquid displacement
├── water.js          # Fast fluid dynamics, oil mixing/separation, and plant hydration
├── lava.js           # Dense molten thermodynamics, water penetration, and rock formation
├── oil.js            # Flammable buoyant liquid physics with water emulsion/separation
├── ice.js            # Freezing and melting thermal logic
├── acid.js           # Fast-spreading corrosive fluid, sinking, and dissolution physics
├── fire.js           # Combustion, heat transfer, temperature decay, and smoke emission
├── steam.js          # Atmospheric rising and condensation
├── smoke.js          # Rising particulate dispersion and decay
├── plant.js          # Root propagation, woodification, and phototropism
├── grass.js          # Surface dirt colonization and blade growth
├── explosive.js      # Clustered BFS blast waves and kinetic shockwaves
└── ui.js             # Categorized elements palette, Bresenham strokes, and settings drawer

🚀 Getting Started

No build step or external dependencies are required. Simply serve the directory with any local static HTTP server:

# Using Python
python -m http.server 8080

# Using Node.js (npx)
npx serve .

Open http://localhost:8080 in any modern web browser.