Procedural audio lets you generate complex sounds dynamically — no pre-recorded samples required. This tutorial explores how to build ambient textures like wind, rain, or static entirely in-browser using raw Web Audio API techniques. Lightweight, flexible, and surprisingly fun.
Use Cases for Procedural Sound
- Background audio in games or immersive websites
- Generative music experiments or audio art
- Minimal sound libraries for performance-focused apps
Step 1: Set Up Audio Context and Noise Generator
White noise is a great foundation for procedural sound:
const audioCtx = new (window.AudioContext || window.webkitAudioContext)();
function createWhiteNoiseBuffer() {
const buffer = audioCtx.createBuffer(1, audioCtx.sampleRate * 2, audioCtx.sampleRate);
const data = buffer.getChannelData(0);
for (let i = 0; i < data.length; i++) {
data[i] = Math.random() * 2 - 1;
}
return buffer;
}
Step 2: Play the Noise Loop
We’ll loop the generated buffer to create a constant noise floor:
const noiseSource = audioCtx.createBufferSource();
noiseSource.buffer = createWhiteNoiseBuffer();
noiseSource.loop = true;
const gain = audioCtx.createGain();
gain.gain.value = 0.3;
noiseSource.connect(gain).connect(audioCtx.destination);
noiseSource.start();
Step 3: Add Texture with Filtering and Modulation
Shape the noise into something more like “wind” or “hiss”:
const filter = audioCtx.createBiquadFilter();
filter.type = 'lowpass';
filter.frequency.value = 1000;
const lfo = audioCtx.createOscillator();
const lfoGain = audioCtx.createGain();
lfo.frequency.value = 0.2; // slow modulation
lfoGain.gain.value = 500;
lfo.connect(lfoGain).connect(filter.frequency);
lfo.start();
noiseSource.disconnect();
noiseSource.connect(filter).connect(gain).connect(audioCtx.destination);
Step 4: Try Different Textures
- Change
filter.type
tobandpass
orhighpass
for different effects - Add a second noise generator for stereo width
- Use multiple LFOs for layered modulation
Pros and Cons
✅ Pros
- Zero asset downloads — small page weight
- Completely dynamic and tweakable in real time
- Perfect for low-memory environments or experimental audio
⚠️ Cons
- Procedural noise isn’t suited for realistic sound effects
- AudioContext timing can vary slightly across devices
- No built-in presets — must hand-tune filters/modulation
🚀 Alternatives
- Sample-based engines: For more realism or specific sound libraries
- WAMs or AudioWorklets: For more complex synthesis
- FM/AM synthesis: Procedural tones instead of noise
Summary
Procedural audio textures open up a powerful path for lightweight, real-time, interactive sound. From ambient noise beds to dynamic generative effects, you can do a lot with just noise, filters, and modulation. No samples, no libraries — just code.
If this was useful, you can support me here: buymeacoffee.com/hexshift