Compose — 음악 & 오디오 제작
speech-swift의 음악 및 오디오 제작 측면은 세 가지 온디바이스 모듈로 구성되며, 모두 MLX 또는 CoreML을 통해 Apple Silicon에서 네이티브로 실행됩니다. MAGNeT은 텍스트 프롬프트로부터 30초 분량의 음악 클립을 생성합니다. 소스 분리(Open-Unmix)는 스테레오 트랙을 네 개의 스템(보컬 / 드럼 / 베이스 / 기타)으로 분리합니다. 음성 향상(DeepFilterNet3)은 실시간으로 음성에서 배경 소음을 제거합니다.
| 모듈 | 작업 | 백엔드 | 출력 | CLI |
|---|---|---|---|---|
| MAGNeT | 텍스트 → 음악 | MLX (INT4 / INT8) | 30초 @ 32 kHz 모노 | speech compose |
| Open-Unmix | 스템 분리 | MLX | 4 스템 @ 44.1 kHz 스테레오 | speech separate |
| DeepFilterNet3 | 노이즈 억제 | CoreML (Neural Engine) | 48 kHz, 실시간 | speech denoise |
MAGNeT — 텍스트-투-음악 생성
Meta의 MAGNeT(단일 비자기회귀 Transformer를 사용한 마스크된 오디오 생성)의 MLX Swift 포팅입니다. 자유 형식의 영어 프롬프트로부터 30초 분량의 32 kHz 모노 음악 클립을 생성합니다 — "happy rock", "energetic EDM with synth lead", 또는 더 깨끗한 결과를 위한 풍부한 설명 텍스트.
아키텍처
첫 번째 호출 시 다운로드되는 세 가지 컴포넌트:
| 컴포넌트 | 역할 | 소스 |
|---|---|---|
| MAGNeT 디코더 LM | 4개의 EnCodec 코드북에 대한 마스크된 비자기회귀 Transformer. 24개 레이어(Small, 300M) 또는 48개(Medium, 1.5B). 양자화된 Q/K/V/out 투영 + FFN 선형(MLX-affine, 그룹 64). | aufklarer/MAGNeT-{Small,Medium}-30secs-MLX-{4,8}bit |
| T5-base 텍스트 인코더 | 텍스트 조건화용 110M 파라미터 인코더. FP32(인코더 전용 경로; 디코더 없음, LM 헤드 없음). | t5-base |
| EnCodec 32 kHz 디코더 | SEANet 디코더(Conv1d / ConvTranspose1d / ResnetBlock / 2-레이어 LSTM) + 4-코드북 Euclidean RVQ. LM의 이산 토큰을 다시 32 kHz 파형으로 매핑합니다. | mlx-community/encodec-32khz-float32 |
마스크된 병렬 디코딩
자기회귀 형제인 MusicGen과 달리, MAGNeT는 코사인 스케줄링된 리마스킹, 분류기 없는 가이던스 어닐링, 단계별 로컬 어텐션 윈도우와 함께 총 50개의 forward pass(4개 코드북 전반에 걸친 기본 분할 [20, 10, 10, 10])를 실행합니다. Stage 0은 전체 self-attention을 사용하고, stage 1-3은 상위 코드북이 세부 사항만 정교화하기 때문에 로컬 |q − k| ≤ 5 윈도우를 사용합니다.
변형
| 변형 | 파라미터 | LM 디스크 크기 | 최대 RSS | 시간(M 시리즈, 30초) | RTF |
|---|---|---|---|---|---|
small-int4 | 300M | 287 MB | ~1.4 GB | ~10.8 s | 0.36× |
small-int8 | 300M | 425 MB | ~1.5 GB | ~11 s | 0.37× |
medium-int4 | 1.5B | 1.36 GB | ~2.2 GB | ~36 s | 1.20× |
medium-int8 | 1.5B | 2.10 GB | ~3.0 GB | ~36 s | 1.20× |
RTF가 1.0 미만 = 실시간보다 빠름. 양자화는 wall-clock에 거의 영향을 미치지 않습니다 — 선형 투영이 아닌 어텐션이 지배적입니다 — 따라서 INT4의 실용적인 이점은 지연 시간이 아닌 메모리입니다.
빠른 시작
import MAGNeTMusicGen
let model = try await MAGNeTMusicGen.fromPretrained(variant: .smallInt4)
let pcm = model.generate(text: "energetic upbeat rock anthem with electric guitar riffs, driving drums, bass groove")
// pcm: [Float] length 960_000 (30 s × 32 kHz mono)
try WAVWriter.write(samples: pcm, sampleRate: 32_000,
to: URL(fileURLWithPath: "out.wav"))
CLI
# Default: small-int4 (~10 s on M-series for 30 s of audio)
speech compose "happy rock" -o happy_rock.wav
# Larger model — better prompt following, ~3.5× slower
speech compose "lo-fi hip hop with mellow piano and warm vinyl crackle" \
--variant medium-int4 -o lofi.wav
# Reproducible
speech compose "energetic EDM with synth lead" --seed 42 -o edm.wav
플래그: --variant {small,medium}-{int4,int8}, --temperature(어닐링, 기본값 3.0), --top-p(기본값 0.9), --cfg-max / --cfg-min(기본값 10.0 / 1.0), --steps "20,10,10,10"(코드북당 반복 횟수), --seed.
"happy rock"과 같은 짧은 태그도 작동하지만 빈약하게 느껴집니다. 악기 + 템포 + 분위기를 언급하는 설명적 프롬프트는 응집성을 눈에 띄게 향상시킵니다 — 우리의 품질 테스트에서 더 풍부한 프롬프트는 더 높은 zero-crossing rate(0.116 vs 0.093, 즉 더 많은 고주파 세부 사항)와 클리핑 없음을 제공했습니다. 비교:
"happy rock"— 빈약함"energetic upbeat rock anthem with electric guitar riffs, driving drums, bass groove"— 더 풍부함, 일반적으로 더 좋음
번들 & 라이선스
네 개의 MLX 번들 모두 facebook/magnet-small-30secs 및 facebook/magnet-medium-30secs에서 파생되었으며 Meta의 라이선스를 상속받습니다: CC-BY-NC 4.0 — 비상업적 용도로만 사용 가능. 생성된 오디오에도 동일한 제한이 적용됩니다.
소스 분리 — Open-Unmix (4 스템)
Open-Unmix HQ / UMX-L이 MLX로 포팅되었습니다. 스템별 BiLSTM 예측기와 다채널 Wiener-EM 후처리 필터를 통해 스테레오 믹스를 네 개의 스템 — 보컬, 드럼, 베이스, 기타 악기 — 으로 분리하며, 모두 역 STFT를 통해 MLX에서 엔드투엔드로 실행됩니다. M 시리즈에서 30초 오디오의 실제 RTF는 약 0.031(실시간보다 32배 빠름).
# Split mix.wav into vocals/drums/bass/other.wav next to it
speech separate mix.wav
# Or keep stems together
speech separate mix.wav --output stems/
import SourceSeparation
let separator = try await SourceSeparator.fromPretrained()
let stems = try separator.separate(audio: stereoSamples, sampleRate: 44_100)
// stems.vocals, stems.drums, stems.bass, stems.other — each [Float]
전체 아키텍처, 튜닝 및 벤치마크 노트는 소스 분리 가이드에 있습니다.
음성 향상 — DeepFilterNet3
Neural Engine(CoreML)의 DeepFilterNet3. 2.1M 파라미터 모델로 48 kHz 음성에서 배경 소음을 실시간으로 제거합니다 — ASR 파이프라인의 전처리 단계로 함께 실행할 수 있을 만큼 작습니다.
speech denoise noisy.wav -o clean.wav
import SpeechEnhancement
let enhancer = try await SpeechEnhancer.fromPretrained()
let clean = try enhancer.enhance(audio: noisy, sampleRate: 48_000)
전체 구성은 음성 향상 가이드에 있습니다.
적합한 도구 선택
| 원하는 것… | 사용 |
|---|---|
| 텍스트 프롬프트로부터 음악 생성 | MAGNeT (speech compose) |
| 기존 트랙에서 보컬이나 드럼 추출 | Open-Unmix (speech separate) |
| 전사 전에 시끄러운 음성 정리 | DeepFilterNet3 (speech denoise) |
| 텍스트를 음성으로 변환(음성 합성) | VoxCPM2 or Qwen3-TTS |