Delay

In this post I will talk about one of the most basic and used building blocks in all audio effects, an integer delay line. In this block, the output signal is a N samples delayed mirror from the input, it can be described as:
y[n] = x[n – N]
wpg_div_wp_graphviz_1
Implementation wise we will need a buffer to hold the delayed samples, the head position and some logic to handle wrapping over the data buffer. I am a big fan of the RAII paradigm, so I apply it to every piece of code I do as much as I can( believe me, it is the best way to avoid shooting yourself in the foot). In that sense we will use a std::unique_ptr as a class member to hold the data array, allocating the memory in the constructor body and leaving it to nicely delete itself upon destruction.
...

unsigned                 size;
unsigned                 head;
std::unique_ptr<float[]> data;

...

Delay::Delay(unsigned size)
    : size(size)
    , head(0u)
{
    data = std::unique_ptr<float[]>(new float[size]);
}

For the processing logic the class contains a public method to process a single sample. This method has to read the output sample value from the head, write the input sample and update the head position. The trick here is to read the output before writing the input sample, that way there will always be an offset of N samples between read and written values.

float Delay::Process(float in)
{
    // read sample from delay data
    const float out = data[head];

    // write sample
    data[head] = in;

    // update head
    ++head;
    if (head >= size)
        head = 0u;

    return out;
}

Complete source code can be found on github. In future posts we will explore how to expand it with a Fractional Delay and later on how are theese blocks combined to achieve more sophisticated audio effects.

Leave a Reply

Your email address will not be published. Required fields are marked *