슬라이드쇼 작성 계약
HyperFrames 슬라이드쇼는 일반 HyperFrames 작곡(씬, 클립, GSAP 타임라인)에 한 가지 추가 요소인 JSON 아일랜드를 포함합니다. 이 아일랜드는 어떤 씬이 슬라이드인지와 어떻게 연결되는지 선언합니다. 플레이어의 SlideshowController가 이 아일랜드를 읽고 연속적인 GSAP 타임라인을 개별적이고 탐색 가능한 덱으로 변환합니다.
먼저 /hyperframes-core를 읽으십시오 (기본 작곡 계약: 클립, 트랙, data-* 속성, 결정론 규칙). 이 스킬은 새로운 내용만 다룹니다: 아일랜드 스키마, 슬라이드 작성 규칙, 조각, 분기, 유효성 검사 및 래핑 컴포넌트.
출력 — 선형 MP4가 아닌 탐색 가능한 덱
슬라이드쇼의 출력은 실행 중인 덱입니다: hyperframes present <project-dir>(또는 Studio 프레젠트 모드)로 제공하십시오. 플레이어의 SlideshowController가 아일랜드를 읽고 탐색, 조각, 분기 및 프레젠터 모드를 구동합니다. 아래의 프레젠트 및 핸드오프를 참조하십시오.
슬라이드쇼를 hyperframes render로 단일 MP4로 렌더링하지 마십시오. 덱은 여러 최상위 씬 작곡(슬라이드당 하나의 data-composition-id)으로 작성되며 마스터 루트 작곡이 없으므로 render는 첫 번째 작곡만 해결하고 조용히 잘린 MP4를 생성합니다(예: 40초 덱의 6초). 선형 메인 라인 내보내기(분기 시퀀스 제외)는 연기되었습니다 — 출시될 때까지 지원되는 출력은 라이브 present 덱과 슬라이드당 snapshot 스틸샷입니다. 사용자가 지금 선형 MP4가 필요하면 이 제한을 표면화하고 render를 덱에 가리키지 마십시오.
의도 확인
사용자가 명시적으로 슬라이드쇼, 슬라이드 쇼 또는 HyperFrames 슬라이드쇼를 요청하면 이 스킬을 진행하십시오.
"프레젠테이션", "피치 덱", "덱", "대화형 덱" 또는 "이 페이지 변환"과 같은 인접한 요청에서 이 스킬이 트리거된 경우 작성 전에 잠시 멈추고 선택지를 제시한 후 확인을 요청하십시오. HyperFrames 슬라이드쇼가 개별 슬라이드, 내장 탐색 및 프레젠터 모드, 편집 가능한 스피커 노트, 공유 미디어 처리 및 핸드오프 전 유효성 검사가 포함된 실행 가능한 덱임을 간략히 설명하십시오. 소스 페이지 변환의 경우, 페이지 이동을 슬라이드 간 전환으로 변환하면서 원본 페이지의 시각적 디자인, 상호 작용, 모션 및 미디어 동작을 보존하는 것이 목표임을 언급하십시오.
그런 다음 짧은 확인 질문을 하십시오:
이 것을 HyperFrames 슬라이드쇼로 만드시겠습니까?
환경에서 제공하는 경우 예/아니오 선택 UI를 사용하고, 그렇지 않으면 질문을 일반 텍스트로 하십시오.
사용자가 예라고 대답할 때까지 슬라이드쇼를 구현하지 마십시오. 아니오라고 대답하면 이 스킬 사용을 중단하고 적절한 비-슬라이드쇼 워크플로우로 전환하십시오.
두 가지 요소
1. 씬 — 일반적인 방식으로 선언
모든 슬라이드는 씬으로 뒷받침됩니다. data-composition-id, data-start, data-duration 및 data-label로 씬을 선언하십시오:
<div
data-composition-id="problem"
data-start="0"
data-duration="8"
data-label="문제"
data-width="1920"
data-height="1080"
>
<!-- 클립이 여기에 위치합니다 -->
</div>
분기 슬라이드(핫스팟을 통해서만 접근 가능, 메인 라인에서 제외됨)도 정확히 같은 방식으로 선언됩니다. 단, 아일랜드의 slideSequences 항목에만 나타나며 메인 slides 배열에는 나타나지 않습니다.
2. JSON 아일랜드 — 작곡당 하나의 스크립트 블록
작곡 HTML에 정확히 하나의 <script type="application/hyperframes-slideshow+json"> 블록을 추가하십시오. 모든 슬라이드쇼 메타데이터를 포함합니다:
<script type="application/hyperframes-slideshow+json">
{
"slides": [...],
"slideSequences": [...]
}
</script>
아일랜드는 슬라이드 순서, 노트, 조각 홀드 포인트, 핫스팟 및 분기 시퀀스의 단일 진리 소스입니다. 찾기 쉽도록 씬 div 앞, <body> 상단 근처에 유지하십시오.
아일랜드를 생성하는 런타임 코드와 함께 대체 <script type="application/json"> 블록 뒤에 슬라이드쇼 매니페스트를 숨기지 마십시오. present 명령은 작곡 HTML을 정적으로 읽고 실제 application/hyperframes-slideshow+json 아일랜드가 이미 존재할 것으로 예상합니다.
스키마
SlideshowManifest (최상위 아일랜드 객체)
{
"slides": [
/* SlideRef[] — 순서대로 메인 라인 */
],
"slideSequences": [
/* SlideSequence[] — 오프라인 분기 시퀀스 */
]
}
SlideRef
{
"sceneId": "problem",
"notes": "고통부터 먼저 이야기하고 회사는 나중에 이야기하십시오.",
"fragments": [3.5, 5.2, 7.0],
"hotspots": [
/* SlideHotspot[] */
],
"ttsScript": null,
"ttsAudioUrl": null,
"ttsDurationMs": null
}
| 필드 | 필수 | 참고 |
|---|---|---|
sceneId | 예 | 반드시 씬의 data-composition-id와 정확히 일치해야 합니다(또는 명시적 startTime/endTime 제공). 린트 규칙은 data-composition-id로 씬을 해결합니다. |
notes | 아니요 | 프레젠터 전용 텍스트. 청중에게 절대 표시되지 않습니다. |
fragments | 아니요 | 슬라이드의 [start, end] 범위 내 시간(초) 배열 — 아래의 조각 참조. |
hotspots | 아니요 | 분기를 트리거하는 대화형 오버레이 — 아래의 분기 참조. |
startTime | 아니요 | 선택 사항. 일치하는 씬의 시간 경계를 재정의합니다. 기본값은 씬의 시작/끝입니다. |
endTime | 아니요 | 선택 사항. 일치하는 씬의 시간 경계를 재정의합니다. 기본값은 씬의 시작/끝입니다. |
ttsScript, ttsAudioUrl, ttsDurationMs | 아니요 | 예약됨. 스키마 필드는 존재하지만 TTS 재생은 아직 연결되지 않았습니다. 미래 빌드용으로 미리 채우지 않는 한 생략하십시오. |
SlideHotspot
{
"id": "h1",
"label": "이것을 어떻게 계산했나요?",
"target": "market-deep-dive",
"region": { "x": 60, "y": 10, "w": 35, "h": 20 }
}
| 필드 | 필수 | 참고 |
|---|---|---|
id | 예 | 슬라이드 내에서 고유해야 합니다. |
label | 예 | 청중에게 표시되는 툴팁/버튼 텍스트. |
target | 예 | slideSequences의 SlideSequence.id와 일치해야 합니다. |
region | 아니요 | 슬라이드 백분율 경계 상자: {x, y, w, h} in 0–100. 생략하면 핫스팟을 전체 슬라이드 레이블 버튼으로 렌더링합니다. |
SlideSequence
{
"id": "market-deep-dive",
"label": "시장 규모 산정 방법론",
"slides": [{ "sceneId": "mkt-1" }, { "sceneId": "mkt-2" }]
}
시퀀스 내의 slides는 메인 라인과 동일한 SlideRef 형태를 사용합니다. 조각 및 중첩 핫스팟이 허용됩니다.
슬라이드 작성 규칙
이는 제안이 아닌 엄격한 제약 사항입니다. 위반하는 슬라이드는 검토자가 볼 때 바로 교체됩니다.
- 헤드라인은 완전한 문장 주장이어야 하며 레이블이 아니어야 합니다. "일정 문제"가 아니라 "중소기업은 수동 일정에 주당 14시간을 소비합니다"라고 작성하십시오. 시각 자료가 무시되더라도 문장이 독립적으로 서야 합니다.
- 슬라이드당 하나의 아이디어 + 하나의 시각 자료. 두 번째 글머리 기호 클러스터나 두 번째 차트를 추가하고 싶다면 슬라이드를 분할하십시오.
- 펀치라인으로 시작하십시오. 가장 강력한 점이 먼저 옵니다 — 슬라이드 내에서도 덱 순서에서도. 투자자는 왼쪽에서 오른쪽, 위에서 아래로 읽고 거기서 멈춥니다.
- 상향식 시장 규모 산정만 허용. 계산 없이 "$500억 TAM"이라고 쓰지 마십시오. 단위 경제학에서 구축하십시오: 계정 × ACV 또는 거래 × 테이크율.
- 최소 글꼴 크기 30pt 상당. 1920×1080에서 헤드라인은 72~96px이고 본문은 48px입니다. 청중이 읽어야 하는 모든 텍스트는 40px 미만으로 내려가지 마십시오.
소스 페이지 이식
기존 페이지를 슬라이드쇼로 변환할 때 소스 충실도는 계약의 일부입니다. 사용자가 명시적으로 재설계를 요청하지 않는 한 소스별 위젯을 단순화된 근사치로 대체하지 마십시오.
- 원본 페이지의 시각적 디자인, 모션 언어, 대화형 동작, 미디어 동작 및 프레젠테이션 편의를 가능한 한 밀접하게 보존하십시오. 슬라이드쇼 시스템이 프레젠터 모드를 지원하는 경우 덱별 구현이 아닌 공유 편집 가능 노트 동작을 사용하여 스피커 노트를 포함하십시오.
- 소스 DOM/CSS/JS에서 기계적 시각 요소를 가능한 한 정확하게 이식하십시오: 사용자 정의 플레이어, 캔버스 시각화 도구, 타임라인, 플레이헤드, 줄기, 확장 원, 호버 상태 등 기타 대화형 세부 사항이 변환에서 유지되어야 합니다.
- 네이티브
<video>/<audio>요소를 사용자 정의 미디어 크롬, 캔버스 시각화 도구, 파형, 비트 그리드 또는 플레이헤드의 진리 소스로 취급하십시오. 소스의 미디어 이벤트(play,pause,timeupdate,seeking,seeked,ended,ratechange,volumechange)를 연결하고media.currentTime에서 시각적 상태를 파생하십시오. 실제 재생에서 벗어날 수 있는 별도의 타이머를 실행하지 마십시오. src가 있는 모든 복사된<video>또는<audio>는 린트 전에 HyperFrames 타이밍 속성인data-start및data-duration과 가청 네이티브 오디오를 보존해야 할 때data-has-audio="true"가 있어야 합니다. 슬라이드별 미디어에는 씬의 시간 범위를 사용하고 여러 포커스 슬라이드에서 재생될 수 있는 사용자 제어 증거 비디오에는 덱 전체 범위를 사용하십시오. 미디어에preload="none"을 남겨두지 마십시오.metadata또는auto를 사용하십시오.- 유효성 검사 전에 소스 글꼴 토큰을 해결하십시오. 사용자 정의 소스 글꼴을 보존하려면 로컬/캡처된 글꼴 파일에 대한
@font-face규칙을 추가하십시오. 시스템 대체 글꼴을 사용하는 경우font-family: var(--f-body)와 같은 토큰화된 선언을system-ui, sans-serif또는ui-monospace, monospace와 같은 구체적인 렌더링 안전 스택으로 바꾸십시오.var(...)를 글꼴 패밀리 값으로 남겨두지 마십시오. - 소스에서 비정형적인 페이지 이동, 특히 스크롤, 휠, 터치, 해시 상태, 리사이즈 또는 requestAnimationFrame 루프로 구동되는 동작을 감사하십시오. 변환/확장된 "세계" 레이어, 패럴랙스, 고정 패널, 수평 스크롤러, 스크롤 스크러빙된 타임라인, 섹션 스냅 및 확대-요소 카메라를 갖춘 고정 뷰포트를 소스 동작으로 취급하십시오. 스크롤은 종종 소스의 전환 트리거이므로 진행 중지점, 이징 및 카메라/포커스 상태를 추출하여 보존한 다음 타임라인 위치, 조각 또는 재사용 가능한 플레이어/하네스 후크를 통해 슬라이드쇼 탐색에서 해당 모션을 다시 호스팅하십시오. 슬라이드 홀드 포인트로 이동하는 독립형 래퍼는 여전히 명시적 탐색-카메라 전환 후크가 필요합니다. 슬라이드당 카메라 변환을 계산하는 것만으로는 충분하지 않습니다. 슬라이드 내에서 문자 그대로의 페이지-아래로-스크롤 전환을 시뮬레이션하지 마십시오. 뷰어는 웹페이지가 스크롤되는 것을 보는 것이 아니라 한 초점 지점에서 다른 지점으로 카메라 이동/확대를 느껴야 합니다. 각 슬라이드 간 카메라 이동을 연속적으로 유지하십시오. x/y 방향이나 확대/축소를 역전시키는 중간 경로 중지를 피하십시오. 소스가 동일한 경계에서 명확하게 그렇게 하지 않는 한, 착지하기 전에 이리저리 움직이는 전환은 더 간단한 직접 초점 이동보다 나쁩니다.
- 소스 미디어 자르기 의미를 보존하십시오. 스크린샷, 트윗/소셜 게시물, 제품 UI 캡처, 차트, 문서, 코드, 리더보드 및 읽을 수 있는 텍스트가 있는 모든 이미지를 콘텐츠 증거로 취급하고 장식용 미디어로 취급하지 마십시오: 안정적인 프레임 내에서 소스 종횡비(
height: auto) 또는object-fit: contain을 사용하십시오.object-fit: cover는 소스가 사용했거나 의도적으로 장식용/배경/시네마틱 썸네일에만 사용하십시오. 이러한 캡처를 슬라이드에 맞춘 후 잘린 텍스트, 로고, 컨트롤 또는 캡션이 있는지 네 모서리를 모두 검사하십시오. 소스 자체가 자르지 않는 한 의미 있는 콘텐츠의 눈에 띄는 자르기는 버그입니다. - 동작이 슬라이드쇼에 일반적이면 플레이어/컨트롤러 또는 재사용 가능한 스킬 스니펫에 넣으십시오. 일회성 덱 스크립트로 해결하지 마십시오.
- 누적된 씬 프레임은 활성 슬라이드의 상호 작용을 차단해서는 안 됩니다. 숨겨진 프레임은 시각적 숨김과 이벤트 게이팅이 모두 필요합니다:
.scene-frame {
opacity: 0;
visibility: hidden;
pointer-events: none;
}
.scene-frame.is-active {
opacity: 1;
visibility: visible;
pointer-events: auto;
}
가시성이 명령적으로 구동되면 가시성 컨트롤러에서 세 가지 속성(opacity, visibility, pointerEvents)을 모두 설정하십시오. opacity: 0만으로는 여전히 클릭을 삼킬 수 있는 보이지 않는 레이어가 남습니다.
조각: 슬라이드 내 공개 홀드 포인트
조각은 컨트롤러가 공개 상태를 유지해야 하는 슬라이드의 [start, end] 범위 내의 절대 작곡 타임라인 시간(초)입니다.
작동 방식:
- 플레이어가 조각 슬라이드에 진입합니다 —
fragments[0]으로 직접 이동하여 유지합니다. - 사용자가 다음(또는 →)을 누르면 컨트롤러가
fragments[1]으로 이동하여 유지합니다. - 마지막 조각 후 다음을 누르면 다음 슬라이드로 진행됩니다.
- 조각이 없는 슬라이드는
slide.end정확히가 아닌 슬라이드 내부의 휴식 프레임(일반적으로 중간점)에서 진입합니다.
조각 시간은 [start, end] 내에 있어야 합니다...
[번역을 위해 잘림]