adapt.normalise_loudness takes a track you already have and delivers it at a target loudness, with its peaks kept safely below clipping. Use it when audio from different places needs to play back at a consistent level:
- a podcast episode recorded at a different level from last week’s;
- music or voiceover that will sit next to other content on a streaming service, a podcast feed or a broadcast channel;
- a batch of tracks that should all sound equally loud, one after another.
create.new_song, create.new_instrumental, create.remix_song, create.remix_instrumental and adapt.auto_cut_down can normalise their own outputs for free. Add the same loudness block to those requests. See Loudness for how normalisation works on every endpoint.
The request
Every field, with its exact rules: submit and poll in the API Reference.
Example
This normalises a podcast episode with thepodcast preset (-16 LUFS) and saves the result. It uses the reference client; save soundpiece.py or soundpiece.mjs next to it first.
The result
run returns the finished normalised_audio object:
The measurements are taken from the delivered audio, not copied from your request, so they tell you what really happened. The next section shows the three things that can happen.
Three possible outcomes
Normalising changes a track’s level. Turning a track up raises its loudness and its peaks together, and peaks are never allowed above -1 dBTP. Most audio can reach its target long before its peaks get there. Very dynamic audio cannot: its peaks are loud compared with its average level, so they hit the ceiling first.allow_compression decides what happens then.
1. It lands on the target
Most music and speech, at any sensible target. Only the level changes, andcompressed is false. This is the podcast episode from the example: asked for {"preset": "podcast"}, delivered at -16.0 LUFS.
2. It is compressed to reach the target
A dynamic recording, such as a quiet orchestral piece with loud climaxes, asked to reach -14 LUFS with compression allowed (the default):compressed is true:
3. It stops short, because you kept the dynamics
The same recording, with compression turned off:ready, and lufs tells you where the track landed. If the difference matters to you, check lufs against your target in your own code, and decide whether to accept it or to resubmit with compression allowed (under a new idempotency key, since it is a different request).
Choosing parameters
Presets or a number
There are two ways to say what loudness you want:- A preset names a destination:
{"preset": "podcast"}. Each preset stands for a fixed value that never changes, so your code means the same thing next year. - A number gives the target in LUFS, from
-30to-6:{"target_lufs": -18}. Use it when a delivery specification gives you a number that isn’t a preset.
preset and target_lufs together is refused with a 422. Both accept allow_compression. An empty block, {}, or no block at all, means -14 LUFS with compression allowed.
Choosing a target by destination
If you don’t know where the audio will end up,
streaming is a safe default. Audio that is louder than a platform’s playback level is turned down by the platform, and audio that is quieter sounds weak next to everything else.
Should I allow compression?
- Leave it on (the default) when hitting the number matters most: a platform or client will measure the delivery, or it will play right after other audio at that level.
- Turn it off when the dynamics matter more than the number: classical music, film score, or anything where the quiet parts should stay quiet. Expect very dynamic audio to come out a little below the target.
The peak ceiling
The true peak is always kept at or below -1 dBTP, and that isn’t a setting. It leaves the headroom that MP3 or AAC encoding and playback need to stay free of clipping.Errors
When you submit (the request is refused, nothing is charged):
While processing (the operation finishes as
failed, with an error.code):
Source limits for this endpoint: WAV, MP3 or FLAC, from 1 second to 5 minutes long, and at most 50 MB.
See Errors for the response shapes, and for the errors every endpoint can return (
401, 403, 429).
