Skip to content

Multi-Stem Frequency Masking Analysis

Analyzes masking relationships across a set of stems (2 to 20 at once), identifying which pairs have the worst frequency collisions. Every unique pair gets computed, but the response is capped: by default you get back min(total_pairs, max(10, stem_count)) pairs — in practice, all of them when you have few stems, otherwise the larger of 10 or one per stem. At 20 stems that’s 190 pairs computed but only 20 returned by default; override the cap with PHANTOM_MASKING_TOP_N.

Parameters

Parameter Type Default Description
file_paths list[string] required List of paths to audio stems (2 or more, max 20)

Example Output

$ multi_stem_masking [vocals.wav, guitar.wav, keys.wav, bass.wav]

Multi-stem Masking Analysis: 4 stems, 6 pairs

Worst Collisions: 1. vocals + guitar 0.67 @ 500 Hz - 2 kHz 2. guitar + keys 0.54 @ 250 Hz - 1 kHz 3. bass + guitar 0.41 @ 125 - 500 Hz 4. vocals + keys 0.38 @ 1 - 4 kHz 5. bass + keys 0.22 @ 125 - 250 Hz 6. vocals + bass 0.11 @ (no significant overlap)

What the Numbers Mean

  • Worst Collisions — Pairs of stems ranked by masking severity, worst first. The number is the same 0-1 overlap-severity scale as analyze_masking, and each pair carries the same per-band breakdown (bands) that analyze_masking returns for a single pair.

  • Pair identity — Pairs reference stems by position (stem_0, stem_1, …) in the order you passed file_paths, not by filename. The response’s stem_paths field maps those IDs back to filenames.

  • stem_count / pair_countstem_count is the number of stems you passed in. pair_count is the total number of unique pairs among them — every combination gets analyzed even though the response may only return a subset (see above).

Example Prompts

Full session check

Which stems in my mix are fighting each other? Analyze masking across vocals.wav, guitar.wav, bass.wav, drums.wav, keys.wav

Clarity issues

My mix sounds muddy — which stems are competing in the low mids?

Pro tip

Each pair from multi_stem_masking already includes the full per-band breakdown, so you don’t need a follow-up analyze_masking call just for detail. Reach for analyze_masking directly when you only care about two specific stems and don’t want to pass the whole session.