Fluid Physics in Three.js: Real-time Water Simulation for Web
Master real-time fluid simulations in the browser. Learn how to use Three.js and GPGPU techniques to create stunning water effects in 2026.

Master real-time fluid simulations in the browser. Learn how to use Three.js and GPGPU techniques to create stunning water effects in 2026.
Fluid Physics in Three.js: Real-time Water Simulation for Web
In 2026, the delta between native gaming and web visuals is disappearing. One of the most requested features for high-end web experiences is realistic, interactive fluid physics.
Today, we'll explore how to build a Real-time Water Simulation that runs at 120fps using Three.js and GPGPU (General-Purpose GPU compute).
Why GPGPU?
Traditional CPU-based physics are too slow for millions of water particles. By using GPGPU, we use the GPU's thousands of cores to calculate the position and velocity of every particle simultaneously.
The Navier-Stokes Approach
To simulate fluid, we follow a simplified version of the Navier-Stokes equations:
- 2.Advection: Move the fluid velocity along the fluid itself.
- 4.Diffusion: Spread high-velocity areas to low-velocity areas (viscosity).
- 6.Pressure: Ensure the fluid is incompressible (it shouldn't "clump").
Implementation: The GPUComputeManager
In Three.js, we use the GPUComputationRenderer utility to manage our simulation textures.
javascriptimport { GPUComputationRenderer } from 'three/examples/jsm/misc/GPUComputationRenderer.js'; const gpuCompute = new GPUComputationRenderer(WIDTH, WIDTH, renderer); // Create textures for position and velocity const dtPosition = gpuCompute.createTexture(); const dtVelocity = gpuCompute.createTexture(); // Add custom shaders for fluid math const velocityVariable = gpuCompute.addVariable('textureVelocity', velocityShader, dtVelocity); const positionVariable = gpuCompute.addVariable('texturePosition', positionShader, dtPosition); // Link variables gpuCompute.setVariableDependencies(velocityVariable, [positionVariable, velocityVariable]); gpuCompute.setVariableDependencies(positionVariable, [positionVariable, velocityVariable]); gpuCompute.init();
Shading the Surface: Refraction and Reflection
A simulation is nothing without a good shader. To make water look real, we need:
- Fresnel Effect: Water is more reflective when viewed at a glancing angle.
- Refraction: Light should bend as it passes through the water volume.
- Caustics: Concentrated light patterns on the floor of the water body.
glsl// Fragment Shader snippet for water surface void main() { vec3 normal = calculateNormal(vUv); vec3 viewDir = normalize(cameraPosition - vPosition); float fresnel = pow(1.0 - dot(normal, viewDir), 5.0); vec3 reflection = textureCube(envMap, reflect(-viewDir, normal)).rgb; vec3 refraction = texture2D(tDiffuse, vUv + normal.xy * 0.1).rgb; gl_FragColor = vec4(mix(refraction, reflection, fresnel), 1.0); }
Performance in 2026
With the widespread adoption of WebGPU, these simulations are becoming even more efficient. However, the WebGL GPGPU approach remains the most compatible way to reach 99% of global users today.
Conclusion
Adding fluid physics to your portfolio isn't just a technical challenge; it's an aesthetic one. It brings a sense of life and interactivity to the digital world that static 3D models can never achieve. Ready to take the plunge?

ZKP-Auth: Privacy-Preserving Sessions with Zero Knowledge Proofs
Authentication without passwords or biometric leakage. Discover how Zero Knowledge Proofs (ZKPs) are redefining user privacy in 2026.

Sovereign Auth: Transitioning to Self-Sovereign Identity in 2026
The end of 'Login with Google'. In 2026, users own their identity data using decentralized identifiers (DIDs). Learn how to implement Sovereign Auth today.