Sunday 18 October 2009

Beat Mangling with Pure Data

Presented here is a patch for beat mangling loops using Pure Data, a free and open-source successor to MAX/MSP. Beatmangle, using a single audio loop, produces persistently changing audio by randomly moving the play head and loop settings. This is a particularly effective technique for generating Squarepusher style beats.

Beat Mangle Pure Data Squarepusher loop tool
Here's the patch in action using a two bar drum n bass loop sample from Computer Music UK magazine (issue 128, Groove Criminals Beat 2, if you're interested.)

Patch analysis can be loosely broken down into five parts; sample loading, sample playback, loop position marker display, randomization of the playback position, and randomization of the loop.

Patch analysis of beatmangle for Pure Data
Sample Loading
The Open File browser is displayed by sending a bang to an openpanel object, which in turn sends a message containing the selected filename. A soundfiler object then reads the audio sample into the specified array in response to the read message. We specify the -resize flag in our message to soundfiler to inform the array to set the correct size required for the selected audio file. The size of the audio file, in samples, is output by the soundfiler object, a value which is accessible elsewhere in the patch with the r $0-sample_count recieve objects.

Sample Playback
The sample loop is played back using a phasor~ which provides an index to a tabread4~ object. The phasor~ generates a floating point signal that ranges from 0.0 to 1.0, which is then multiplied by the number of samples in our audio file to give a range between 0.0 and the number of samples.

To play back the sample at its original tempo, we set the phasor~ to run at a frequency so that a single phasor~ period takes the same time as a single cycle of the loop. This frequency, the reciprocal of the loop length in seconds, is calculated in the len2freq subpatch.

Loop Position Marker Display
A hslider (horizontal slider) object shows the current playing position beneath the waveform display. The slider range is set in response to a sample_count message (ie, when a new audio file is opened.) The current play index of the scaled phasor~ is sampled using a snapshot~ object, which periodically generates a value in response to a metro object running at 10 frames per second. The position of the hslider thumb is updated to reflect this value.

Randomization of the Playback Position
There is a 50% chance that randomization occurs every 8th note. A random 2 and sel 0 object pair ensures that only half of the metro bangs are processed. The offset is calculated by taking the number of bars in the loop, multiplying by 8 to get the number of 8th notes, and generating a random number in this range. This is then scaled back by dividing by the number of 8th note to give a 8th note quantized phase position in the range 0.0 to 1.0. This is all contained in a randoffset subpatch. The phase offset is then added to the raw phasor~ output (with a +~ object), and then wrapped to the range 0.0 to 1.0 with a wrap~.

Randomization of the Loop
Loop randomization, contained in the randloop subpatch, adds quick staccato drum n bass style noises to the audio. This is randomly done by multiplying the phasor~ by 1, 2, 4, 8, 16, 32, 64, or 128, wrapping this via a wrap~ object to the range 0.0 to 1.0, and then dividing down again by the previous multiplier. This process effectively shortens the period of the phasor so that it loops over a half, a quarter, an eighth, a sixteenth, etc, of the entire length of the sample.

Finally, when a 64th note or 128th note loop is randomly selected, we also increase the chance of randomization in the previous stage from 50% to 100%. This significantly reduces the chance of long sections of 'machine gunning' (a sound which gets grating fairly quickly if overused) when fast looped notes continually play.

Download the beatmangle Pure Data patch here.