I love music. I love math. I'm an engineer. Maybe that's why I love the Web Audio API.

The Web Audio API is very powerful. The way you can create audio nodes and chain them together is very flexible. The audio source can be an HTML5 <audio> element on the page, you can ask permission to use the microphone or you can even create sound with oscillator nodes.

Imagine a recording studio with lots of equipment like mics, amplifiers, mixers, speakers and synths with lots of wires that connect the equipment. The AudioContext is the studio where everything lives. From the AudioContext you can pick up some equipment and wire it together, say an OscillatorNode (synth) that you connect to a GainNode (amplifier) that you connect to the AudioDestinationNode (speakers).

Filter

The first Pen I want to show you is an experiment with audio filters. I use Soundcloud to stream Martin Garrix's remix Project T. By putting the audio in an HTML5 <audio> element with the controls attribute present we get all the control functionality for free (play/pause/skip/volume/time left).

This is how you create a filter:

    biquadFilter = audioContext.createBiquadFilter();
  biquadFilter.type = "lowpass";
  biquadFilter.frequency.value = 1000;
  biquadFilter.Q.value = 10;
  biquadFilter.gain.value = 20;

Filter type is selected with the drop down. Frequency, Q and gain is controlled with the sliders. Some filter parameters are not applicable for certain filter types, then the corresponding slider is disabled.

Then we need to connect the audio source node with the filter node and then the filter node with the output node. Source -> Filter -> Output.

To draw the frequency response resulting from the filter I use getFrequencyResponse(). The first parameter is an array containing all the frequencies we would like to get the response for. The second and third parameters are the output arrays (same length as the first). Then we can use those two output arrays to draw curves on the canvas.

    biquadFilter.getFrequencyResponse(
    myFrequencyArray, 
    magResponseOutput,
    phaseResponseOutput);

  • magResponseOutput is the white curve
  • phaseResponseOutput is the red curve

When you use Web Audio API to stream music you have to be aware of the CORS restrictions. If you would like to load audio from another origin than CodePen, you have to be sure that the origin has set up CORS headers properly.

Try using the bandpass filter to isolate the melody.

Oscillator

The second Pen I like to show you is a simple tone generator. It uses an oscillator node to produce sound and an analyser node plus a canvas element to display the resulting sound waves. (More info on the analyser later.)

Try the square wave and set the frequency rather low, then you should be able to see the Gibbs phenomenon.

Also try the custom wave shape. It uses audioContext.createPeriodicWave() and oscillator.setPeriodicWave() to create a wave with three combined frequencies. The base frequency is the one you set with the slider, the second one is twice the base frequency and the third one is three times the base frequency. The arrays passed to createPeriodicWave contains these first three Fourier coefficients. Each value specifies how much of that coefficient you can hear (0-1).

This pen shows that you don't need to connect the audio nodes like a train, you can branch off as you like. The gain node is used to toggle sound on or off with the button. And the analyser node gives us real time data about the sound playing.

    Oscillator -- Gain +-- Out (speaker/phones)  
                     |   
                     +-- Analyser 

Analyser

The third pen features an analyser node to visualise music streamed from Soundcloud. There are two different kinds of data you can get from the analyser node: frequency or time domain. With frequency data you can draw a frequency spectrum - "Frequency bars" button and with time domain you can draw the sound wave - "Oscilloscope" button.

There is a single note playing repeatedly at the beginning of the mix. Click the "Frequency bars" button immediately and you will see the base frequency and the overtones.

Note that you can change song anytime by pasting the song's Soundcloud URL into the text box and then click Find.

  • https://soundcloud.com/adi-cohen-8/my-heart-is-stone-adi-cee
  • https://soundcloud.com/scitec/tec115-1-adjd-alexi-delano
  • https://soundcloud.com/hardwell/hardwell-ww-the-dance-floor-is-yours-free-download

The Outsider is a friend of mine. The majority of his tracks are on Mixcloud: https://www.mixcloud.com/outsider_music/

More Pens

Here are all my Web Audio API Pens in a CodePen Collection.

I have another follow up post on the subject with other types of nodes like the convolver (very cool!): More Fun with Web Audio API.