Communitygithub.com

사운드 및 음악 싱크

편집자처럼 비디오를 스코어링합니다: 음악에 맞춰 컷을 비트매칭하고, 전환부에 SFX를 배치하며, 보이스오버에 숨을 쉴 공간을 주고, 로열티 프리 트랙을 안전하게 소싱하며, VO가 선명하게 위에 놓이도록 음악을 덕킹합니다.

사운드 및 음악 싱크란 무엇인가요?

이 스킬은 비디오 편집에서 오디오 믹스의 창의적 결정을 내리는 방법을 가르칩니다. 사용자는 BPM을 기반으로 비트 그리드를 계산하고, 컷을 비트에 맞추고, 전환부에 SFX를 배치하며, 보이스오버를 페이싱하고, 음악을 덕킹하여 VO가 선명하게 들리도록 하는 방법을 배웁니다. `beat_grid.js`와 `mix_levels.js`라는 자체 포함된 Node.js 스크립트를 제공하여 구체적인 프레임 번호와 덕킹 레벨을 계산합니다. 이 스킬은 Claude Code, Cursor, Codex와 같은 AI 에이전트에서 사용하도록 설계되었으며, 최종 오디오 결정(프레임 번호, SFX 타임스탬프, 덕 레벨)을 `remotion-compose`와 `remotion-render`에 전달하여 Remotion 타임라인에 배선하고 내보냅니다. 이 스킬은 **video-storyboard**와 **motion-design-principles**의 비디오 방향 팩과 함께 작동하며, **kinetic-typography**, **product-demo-director**, **social-video-formatter**와 같은 다른 스킬과 조정됩니다. 오디오 품질 표준과 일반적인 실수를 피하는 방법(예: 컷을 비트에서 떠다니게 두지 않기, VO 아래에서 음악을 전체 레벨로 재생하지 않기, 하나의 전환에 여러 SFX를 쌓지 않기)을 강조합니다.

지원 대상~Claude Code~Codex CLI~Cursor
npx skills add https://github.com/SkillMedev/tutorial-video-studio/tree/main/skills/sound-and-music-sync

즐겨 사용하는 AI에게 물어보기

이 에이전트 스킬이 미리 로드된 새 채팅을 엽니다.

문서

사운드 및 음악 싱크은(는) 무엇을 하나요?

사운드는 비디오의 절반이며 사람들이 잊는 절반입니다. 비트에 맞춰 컷한 평범한 애니메이션에 깔끔한 보이스오버가 있으면 전문적으로 읽히지만, 컷이 떠다니고 VO가 음악에 묻힌 아름다운 애니메이션은 아마추어처럼 읽힙니다. 이것이 오디오 취향 레이어입니다. 컷이 어디에 떨어질지, 사운드 효과가 어디를 강조할지, 보이스오버가 어떻게 숨을 쉴지, 믹스가 어떻게 배치될지를 결정한 다음, 구체적인 숫자(비트 프레임, SFX 타임스탬프, 덕 레벨)를 remotion-compose에 넘겨 타임라인에 배선하고 remotion-render에 넘겨 내보냅니다. <Audio> JSX를 작성하거나 렌더러를 실행하지 않습니다. 그들을 공급하는 창의적인 결정을 내립니다.

이것은 motion-video-direction 팩의 나머지와 짝을 이룹니다: video-storyboard 장면 목록과 motion-design-principles 타이밍 결정이 입력입니다 - 이미 존재하는 비트에 맞춰 스코어링합니다. 텍스트가 오디오에 맞춰 애니메이션되면 kinetic-typography와 동기화하고, 컷 리듬이 제품 워크스루를 전달하면 product-demo-director와 조정하며, 세로/소셜 버전을 편집하면 social-video-formatter로 플랫폼별 비트를 다시 도출합니다. 오디오 믹스는 자체 레이어입니다 - 시각적 모양(색 그레이딩, 조명, 대비)은 motion-color-and-light에 맡기고 그것이 그레이딩하는 대로 스코어링합니다.

워크플로우

순서대로 실행하세요. 컷이 비트에 고정되기 전에 SFX를 배치하지 말고, VO 타이밍이 맞기 전에 믹스를 확정하지 마세요 - 각 단계는 이전 단계에 의존합니다.

  1. 트랙을 선택하고 템포를 고정하세요. 비디오의 에너지와 길이에 맞는 음악을 선택하고, 라이선스를 확인한 다음(참조/로열티-프리-소싱 참조), BPM을 구하세요. 대부분의 로열티 프리 라이브러리는 BPM을 나열합니다. 그렇지 않으면 탭하거나 감지기를 사용하세요. BPM은 모든 다운스트림의 중추입니다 - 하나의 비트는 60 / BPM초 동안 지속되며, 프로젝트 fps에서 fps * 60 / BPM 프레임입니다.

  2. 비트 그리드를 구축하고 컷을 스냅하세요. 비트를 프레임 번호로 변환하고 모든 하드 컷과 주요 장면 변경을 비트에 배치합니다(아래 beat_grid.js 실행). 강조를 위해 다운비트(4/4 박자에서 1, 5, 9박)에서 컷하고, 일상적인 전환을 위해 모든 비트에서 컷합니다. 비트에서 2~3프레임 떨어진 컷은 이유를 설명할 수 없는 시청자에게도 "잘못된" 것으로 읽힙니다. 스냅된 프레임 목록을 <Sequence from={...}> 경계로 remotion-compose에 전달하세요.

  3. 전환부에 사운드 효과를 배치하고, 그 위에 배치하지 마세요. SFX는 모션을 물리적으로 느끼게 하기 위해 존재합니다. 규칙: 사운드는 모션이 피크에 도달하는 순간에 피크에 도달합니다. 후샤는 스와이프로 리드 인합니다(컷보다 약 35프레임 일찍 시작하여 꼬리가 컷에 떨어지도록); 임팩트/둔탁한 소리는 카드가 꽂히는 프레임 에 떨어집니다; 클릭/팝은 UI 요소가 나타나는 프레임에 떨어집니다; 라이저는 공개 전 1020프레임에 걸쳐 쌓이고 그 위에서 해결됩니다. 전환당 하나의 SFX - 쌓으면 구두점이 소음으로 바뀝니다. 참조/sfx-배치를 참조하세요.

  4. 보이스오버에 숨 쉴 공간을 주세요. VO는 비디오의 실제 속도를 설정합니다. 비주얼은 VO를 제공하고, 그 반대는 아닙니다. 대화식으로 분당 약 150단어(≈초당 2.5단어)를 목표로 하세요 - 더 빠르면 서두르는 것으로, 더 느리면 인질 비디오로 읽힙니다. 핵심 문장 전과 CTA 후에 비트의 침묵(8~15프레임)을 남겨두세요. 귀를 위해 쓰세요: 짧은 문장, 각각 하나의 아이디어, 축약형. 장면 컷이 단어 중간에 떨어지지 않게 하세요 - 장면 경계를 문장 사이의 간격에 맞추세요. VO를 먼저 시간을 재고, 그런 다음 장면 지속 시간을 늘리거나 줄여서 맞추세요(이것이 remotion-compose가 사용하는 durationInFrames가 됩니다).

  5. 믹스: VO가 위에 앉도록 음악을 덕킹하세요. 이것은 가장 흔한 오디오 실패입니다. 음악과 전체 볼륨의 VO는 동일한 주파수 범위에서 경쟁하며 단어가 손실됩니다. VO가 말할 때마다 음악을 레벨의 약 2535%로 덕킹한 다음, 간격에서 다시 올리세요. 구체적인 레벨 및 타이밍 번호는 mix_levels.js를 실행하세요. VO를 약 -3-6 dB(선명하고, 클리핑되지 않음), 덕킹된 음악을 약 -18~-22 dB로 목표로 하세요. 덕 엔벨로프(덕킹할 프레임, 바닥 레벨)를 remotion-compose에 전달하면, per-<Audio> volume 콜백을 통해 적용됩니다.

  6. 내보내기를 스팟 체크하세요. remotion-render가 MP4를 생성한 후, 좋은 헤드폰뿐만 아니라 노트북 스피커와 휴대폰 스피커로 들어보세요 - 대부분의 시청자는 나쁜 스피커를 사용합니다. 확인: VO의 모든 단어가 음악 위에서 알아들을 수 있고, SFX가 클리핑되거나 놀라게 하지 않으며, 컷이 비트에 고정된 느낌이고, 가장 큰 순간이 왜곡되지 않습니다. 단어가 손실되면 해당 범위에서 더 깊게 덕킹하고, SFX가 놀라게 하면 6dB 낮추세요.

품질 기준

오디오는 다음 모든 사항이 충족될 때만 A+입니다:

  • 모든 하드 컷이 그리드의 비트 프레임에 떨어집니다 - 비트 사이에 떠 있지 않습니다.
  • 모든 전환 SFX가 모션이 피크에 도달하는 정확한 프레임에서 피크에 도달합니다; 라이저는 공개 시점에 해결되며, 그 전후가 아닙니다.
  • VO가 분당 약 140~160단어로 실행되며 핵심 문장 전과 CTA 후에 의도적인 침묵이 있습니다; 단어 중간에 장면 컷이 없습니다.
  • VO가 휴대폰 스피커에서 음악 위에서 완전히 알아들을 수 있습니다 - 가정이 아닌 확인됨 - 음악이 음성 아래에서 약 30%로 덕킹되기 때문입니다.
  • 전환당 정확히 하나의 SFX; 트랙이 루프되거나 마지막 프레임에서 갑작스러운 차단 없이 깔끔하게 종료됩니다.
  • 모든 오디오 에셋의 라이선스가 의도된 사용(상업적/유료 광고/클라이언트 작업)을 허용하고 저작자 표시 요구 사항이 기록됩니다.

하지 말아야 할 것

  • 장면의 "자연스러운" 길이를 유지하기 위해 컷이 비트에서 떠다니게 두지 마세요 - 대신 장면을 가장 가까운 비트로 늘리거나 줄이세요.
  • 보이스오버 아래에서 음악을 전체 레벨로 재생하지 마세요; 덕킹되지 않은 음악은 VO가 탁해 보이는 이유입니다. 누군가 말할 때마다 덕킹하세요.
  • 하나의 전환에 여러 SFX를 쌓거나 모든 컷에 동일한 후샤를 재사용하지 마세요 - 다양하게 하지 않으면 귀가 듣기를 멈춥니다.
  • 여기서 <Audio> JSX를 작성하거나 startFrom/volume 콜백을 설정하거나 렌더러를 호출하지 마세요 - 숫자를 생성하고 remotion-compose / remotion-render에 전달하세요.
  • YouTube 리핑, 명시된 라이선스가 없는 "무료" 사이트 또는 클라이언트의 Spotify에서 트랙을 가져오지 마세요 - 상업적 사용에는 실제 로열티 프리 또는 라이선스 소스가 필요합니다.
  • 전체 믹스를 가능한 한 크게 정규화하지 마세요; 가장 큰 임팩트가 클리핑되지 않도록 헤드룸을 남겨두세요.
  • VO가 고정된 런타임에 맞추기 위해 서두르게 하지 마세요 - VO에 맞춰 비주얼을 다시 편집하고, 비주얼에 VO를 맞추지 마세요.

계산기: 비트 그리드

자체 포함 Node 스크립트. beat_grid.js로 저장하고 node beat_grid.js로 실행하세요. BPM과 fps를 컷이 떨어져야 하는 정확한 프레임 번호로 변환하고 다운비트를 표시합니다. 종속성 없음. 인쇄된 프레임을 <Sequence from={...}> 경계로 remotion-compose에 전달하세요.

// Beat grid. Edit inputs, then: node beat_grid.js
const input = {
  bpm: 120,            // tempo of the chosen track
  fps: 30,             // project frame rate
  durationSeconds: 12, // length of the video
  beatsPerBar: 4,      // 4/4 time; downbeat is every 4th beat
}

const framesPerBeat = (input.fps * 60) / input.bpm
const totalFrames = Math.round(input.durationSeconds * input.fps)
const beats = []
for (let b = 0; ; b++) {
  const frame = Math.round(b * framesPerBeat)
  if (frame > totalFrames) break
  beats.push({ beat: b + 1, frame, downbeat: b % input.beatsPerBar === 0 })
}

console.log('Frames per beat:', framesPerBeat.toFixed(2), '(' + (60 / input.bpm).toFixed(3) + 's each)')
console.log('Cut on these frames (* = downbeat, best for hard cuts):')
for (const b of beats) {
  console.log('  beat ' + String(b.beat).padStart(2), '-> frame', String(b.frame).padStart(4), b.downbeat ? '*' : '')
}
console.log('Downbeat frames only:', beats.filter((b) => b.downbeat).map((b) => b.frame).join(', '))

작업 예제 출력

위 입력으로 스크립트는 다음을 출력합니다:

Frames per beat: 15.00 (0.500s each)
Cut on these frames (* = downbeat, best for hard cuts):
  beat  1 -> frame    0 *
  beat  2 -> frame   15 
  beat  3 -> frame   30 
  beat  4 -> frame   45 
  beat  5 -> frame   60 *
  beat  6 -> frame   75 
  beat  7 -> frame   90 
  beat  8 -> frame  105 
  beat  9 -> frame  120 *
  ...
Downbeat frames only: 0, 60, 120, 180, 240, 300, 360

해석: 120 BPM 및 30 fps에서 비트는 정확히 15프레임입니다. 일상적인 전환은 나열된 모든 프레임에 배치하고 가장 어려운 컷(인트로-투-콘텐츠 컷, CTA 공개)은 다운비트(0, 60, 120…)에 배치하세요. 장면이 70프레임을 실행하려면 컷이 70에서 떠다니게 하는 대신 75(비트 6)로 스냅하세요. 이러한 스냅된 숫자는 정확히 remotion-compose가 <Sequence from={...}>에 넣는 것입니다.

계산기: 믹스 레벨 및 덕 타이밍

자체 포함 Node 스크립트. mix_levels.js로 저장하고 node mix_levels.js로 실행하세요. 덕킹된 음악 레벨과 각 VO 라인의 프레임 범위를 계산하여 remotion-compose에 분위기 대신 구체적인 엔벨로프를 전달합니다. 종속성 없음.

// Mix and ducking planner. Edit inputs, then: node mix_levels.js
const input = {
  fps: 30,
  musicVolume: 0.8,       // music level when no one is speaking (0-1)
  duckToPercent: 0.30,    // duck music to this share of its level under VO
  voVolume: 1.0,          // voiceover level (keep VO the loudest element)
  duckFadeFrames: 8,      // ramp in/out so the duck is not a hard jump
  // VO lines as [startSeconds, endSeconds]; duck music across each, with fade pad
  voLines: [
    [0.5, 3.2],
    [4.0, 7.5],
    [8.2, 11.0],
  ],
}

const duckedLevel = +(input.musicVolume * input.duckToPercent).toFixed(3)
const toFrame = (s) => Math.round(s * input.fps)
// rough dB for reference: 20*log10(level)
const dB = (v) => (v <= 0 ? '-inf' : (20 * Math.log10(v)).toFixed(1) + ' dB')

console.log('VO level:           ', input.voVolume, '(' + dB(input.voVolume) + ')  <- loudest element')
console.log('Music (no speech):  ', input.musicVolume, '(' + dB(input.musicVolume) + ')')
console.log('Music ducked under VO:', duckedLevel, '(' + dB(duckedLevel) + ')')
console.log('Duck fade:          ', input.duckFadeFrames, 'frames in/out')
console.log('Duck music across these frame spans (pad ' + input.duckFadeFrames + 'f each side for the fade):')
for (const [start, end] of input.voLines) {
  const a = toFrame(start) - input.duckFadeFrames
  const b = toFrame(end) + input.duckFadeFrames
  console.log('  VO ' + start + 's-' + end + 's  -> duck frames', Math.max(0, a), 'to', b)
}

작업 예제 출력

VO level:            1 (0.0 dB)  <- loudest element
Music (no speech):   0.8 (-1.9 dB)
Music ducked under VO: 0.24 (-12.4 dB)
Duck fade:           8 frames in/out
Duck music across these frame spans (pad 8f each side for the fade):
  VO 0.5s-3.2s  -> duck frames 7 to 104
  VO 4s-7.5s    -> duck frames 112 to 233
  VO 8.2s-11s   -> duck frames 238 to 338

해석: VO는 전체 레벨(믹스에서 가장 큰 요소)을 유지하고, 음악은 간격에서 0.8로 재생되며 누군가 말할 때마다 약 1/3인 0.24로 덕킹되고, 8프레임에 걸쳐 페이드되어 딥이 갑작스러운 점프가 되지 않습니다. 프레임 범위는 정확히 remotion-compose가 음악 <Audio> volume 콜백에 공급하는 범위입니다: 범위 밖에서는 전체 레벨, 내부에서는 duckedLevel, 페이드 패드에서 선형 램프됩니다. 이것이 단어가 음악이 사라지지 않고 선명하게 유지되는 이유입니다.

템플릿: 오디오 큐 시트

이것을 복사하고, 비트 그리드 및 믹스 레벨 출력으로 FILL 필드를 채운 다음, 완성된 시트를 remotion-compose에 전달하세요. 비디오의 모든 오디오 결정에 대한 단일 진실 공급원입니다.

AUDIO CUE SHEET. [FILL: video name]. fps [FILL] / [FILL] BPM / [FILL]s total

MUSIC
  Track:                 [FILL: title + source]
  License:               [FILL: e.g. Epidemic Sound commercial / CC0] - attribution: [FILL: yes/no, text]
  Level (no speech):     [FILL: 0-1]    Ducked under VO: [FILL: 0-1] (~30%)

BEAT GRID (from beat_grid.js) - cuts land here
  Downbeat frames:       [FILL: 0, 60, 120, ...]
  Hard cuts on:          [FILL: which downbeats carry the big cuts]

SFX (one per transition; peak ON the motion peak)
  FRAME    SFX            ROLE
  [FILL]   [FILL whoosh]  leads into swipe (start ~4f early, tail on cut)
  [FILL]   [FILL impact]  card slam-in, lands ON cut frame
  [FILL]   [FILL riser]   builds across 10-20f, resolves on reveal
  [FILL]   [FILL pop]     UI element appears

VOICEOVER (~150 wpm; scenes fit the VO, not the reverse)
  LINE                                   START   END    SCENE
  [FILL line]                            [FILL]  [FILL] [FILL]
  (silence 8-15f before key line / after CTA)

DUCK ENVELOPE (from mix_levels.js) - frame spans to lower music
  [FILL: 7-104, 112-233, ...]  fade [FILL]f in/out

HANDOFF: remotion-compose wires <Audio> + volume callbacks; remotion-render exports.

참조/로열티-프리-소싱

상업용 비디오에는 실제로 사용할 수 있는 라이선스가 있는 음악이 필요합니다. "YouTube에서 찾았어요"는 라이선스가 아니며 클라이언트의 Spotify도 아닙니다. 사용 사례별 라이선스/로열티 프리 소스:

  • 구독 라이브러리(클라이언트/상업/광고에 가장 안전함): Epidemic Sound, Artlist, Musicbed, Soundstripe. 고정 요금, 광범위한 상업 라이선스, 대규모 SFX 라이브러리, 비디오별 저작자 표시 불필요. 유료 작업의 기본값.
  • 조건이 있는 무료(각 트랙 확인 필요): YouTube Audio Library, Free Music Archive, Incompetech, Freesound. 종종 라이선스 유형(CC0, CC BY 등)을 지정합니다. CC BY는 저작자 표시가 필요하며 일부 상업 라이선스는 허용하지 않습니다. 확인하세요.
  • 피해야 할 것: YouTube 리핑, 라이선스가 명시되지 않은 "무료" 사이트, 클라이언트의 Spotify 계정. 저작권 위반 책임은 귀하에게 있습니다.
  • 라이선스 기록: 각 트랙에 대해 제목, 소스, 라이선스 유형, 저작자 표시 필요 여부를 기록하세요. 프로젝트 자산 폴더에 LICENSE.txt 파일이 좋은 방법입니다.

참조/SFX-배치

SFX는 모션의 물리적 느낌을 강화하며 모든 전환을 개별적으로 만듭니다. 여기에 몇 가지 일반적인 예가 있습니다.

SFX 유형모션 순간프레임 배치효과
후샤스와이프/패닝컷보다 3~5프레임 일찍 시작, 꼬리가 컷에 떨어짐부드러운 전환 강조
임팩트/둔탁카드 슬램인/요소 등장정확히 컷 프레임갑작스러운 느낌을 물리적으로 만듦
클릭/팝UI 요소 나타남정확히 컷 프레임깔끔한 마이크로 상호 작용
라이저공개 전 빌드업공개 전 10~20프레임, 공개 시 해결기대감 구축
스월화면 밖에서 요소가 회전하며 들어옴회전 피크 전 5~10프레임 시작회전 동작 강조

규칙: 각 효과의 피크를 해당 모션의 피크와 일치시키세요. 전환당 하나의 SFX. 규칙은 기억하기 쉽습니다: 같은 효과를 반복해서 사용하지 마세요. 패턴이 지루해집니다.

Individual skills in this repo

This repo contains 11 individual skills — each has its own dedicated page.

Captions From Transcript

Produce an accurate, properly timed caption track (SRT or WebVTT) from a video

Kinetic Typography

Put text in motion the right way - title cards, animated captions, lower-thirds, callouts, and word-by-word reveals - with a reading-time-per-word budget so copy holds long enough to read, plus enter/exit timing, weight and size transitions, and type hierarchy in motion. Use when someone asks to

Motion Design Principles

The craft layer for motion: pick the right easing (ease-in / ease-out / ease-in-out / spring), get timing and spacing right, build the anticipation→action→follow-through arc, and apply Disney

Narration Script

Write the spoken voiceover for a tutorial or demo - the actual words, phrased for the ear and synced one-instruction-per-action to what is on screen, with a pacing budget and a confident, jargon-checked tone. Use when someone says

Product Demo Director

Direct the craft of putting a real software UI on screen - cursor choreography, zoom/pan/callout language, screen-recording vs recreated-UI, and making state changes legible with highlights, focus pulls, and slow-downs. Use when filming or recreating an app for a product demo, feature walkthrough, onboarding clip, or release reel and asking

Remotion Compose

Turns a natural-language video brief into a complete, ready-to-preview Remotion composition - extracts duration, scenes, brand colors, aspect ratio, and real copy; plans the frame budget; and writes data-driven React/TypeScript using useCurrentFrame, interpolate, spring, AbsoluteFill, and Sequence, registered in Root.tsx. Use when someone says

Remotion Render

Renders a Remotion composition to MP4 and runs the edit-and-re-render loop - CLI render commands, 1080p/4K/9:16 presets, concurrency tuning, codec selection, batch variants from a JSON data file, and Lambda for cloud rendering. Use when someone says

Remotion Setup

Scaffolds a new Remotion video project wired for Claude Code Agent Skills - Node check, create-video scaffold, skills install, folder conventions, Google Fonts, and a smoke-test render. Use whenever someone wants to start making videos with Remotion and Claude, even just

Screencast Capture

Capture clean raw screen and camera footage for a tutorial or product demo - choosing the recorder (macOS Screenshot toolbar, QuickTime, OBS, Windows Game Bar), setting resolution / frame-rate / cursor / microphone, prepping a distraction-free stage, and recording in retakeable segments. Use when someone says

SkillMedev/tutorial-video-studio

Plan a product demo, feature announcement, or launch video as a beat sheet and shot list BEFORE animating - hook in the first 3s, problem, reveal, proof, CTA - with target duration and pacing per scene type, output as a JSON scene plan that remotion-compose consumes directly. Use when someone says

Social Video Formatter

Reframe and export a finished video for social platforms - 9:16 ↔ 16:9 cropping, burned-in captions, a platform-native first frame, loop design, and per-platform specs (aspect, length, safe areas) for TikTok, Reels, Shorts, X, and LinkedIn. Use when someone says

관련 스킬