| name | omd:experiment-gallery |
| description | N개 brand experiment를 한 화면에서 비교하는 gallery index.html을 생성. 각 카드는 brand name, wow rating, multi-turn refinement deltas, iframe scaled preview, standalone link 포함. '결과물 한 번에 보여줘', '갤러리 만들어', '5개 비교 뷰', 'experiment 결과 정리' 류 트리거. omd:harness가 N개 brand batch 작업 끝낸 직후 자동 호출되거나 사용자가 명시적으로 호출. |
omd:experiment-gallery — N-brand comparison index
왜 이 스킬
여러 brand experiment를 돌리고 나면 결과물 검수가 산만 — 각 폴더 따로 열고 비교하기 번거로움. 이 skill은 단일 index.html 에 N개 결과를 iframe으로 박아서 한 화면에서 wow ratings + deltas + 실제 렌더를 동시 확인.
트리거
- 명시: "결과물 한 번에 보여줘", "갤러리 만들어", "N개 비교 뷰"
- 묵시: 사용자가 omd:harness로 ≥2개 brand experiment를 한 batch에서 끝낸 직후 ("이제 비교해보자" 라는 흐름)
- 다른 skill 안에서 호출: omd:batch-launch가 5개 brand 끝낸 후 Phase 5로 호출
입력
다음 둘 중 하나:
- 명시 디렉토리 list: 사용자가
/tmp/omd-gallery/{brand1,brand2,brand3} 같은 list 제공
- 부모 디렉토리 + glob:
/tmp/omd-gallery/* 또는 web/experiments/2026-05/* 등 — skill이 자동 enumerate
각 brand 디렉토리는 다음 파일들 있어야 함 (있으면 사용, 없으면 fallback):
landing.html (필수) — iframe src
DESIGN.md (선택) — brand display name 추출
assets/_reference/<id>/structure.json (선택) — composition 메타
assets/_reference/<id>/.live-inspect-proof.json (선택) — live tag 표시
screenshots/after.png (선택) — fallback preview
experiment-meta.json (선택, 권장) — wow rating + round-2 deltas + 카테고리 — sub-agent가 작성
experiment-meta.json 스키마 (sub-agent가 작성)
각 experiment sub-agent는 work 종료 직전 다음 파일을 작성:
{
"brand_id": "toss",
"brand_korean": "토스",
"brand_category": "Fintech",
"brand_color_hex": "#3182f6",
"wow_rating": 7.5,
"lines": 603,
"live_inspect": { "ran": true, "raw_samples": 7, "method": "playwright|harness" },
"round2_deltas": [
"Reveal failsafe — 2s forwards animation",
"Stat-card narrative upgrade",
"CTA copy 구체화 (시간 약속)",
"Hero shimmer (accent text gradient)",
"Dark marquee band rhythm break",
"Chart stroke-dashoffset draw-in"
],
"ip_compliance": {
"your_logo_placeholders": 2,
"your_product_name_placeholders": 4,
"brand_logo_embed_count": 0,
"verbatim_brand_copy": 0
},
"honest_gaps": [
"Hero composition은 single character + flat card (3D ornament 부재)",
"Carousel은 dot만 회전 (slide content 미스왑)"
]
}
skill이 이 파일을 읽어 gallery 카드의 wow / lines / deltas 영역 채움. 없으면 brand_id만으로 minimal 카드.
출력
1. <output-dir>/index.html (메인 산출물)
다음 구조:
- 헤더: title (사용자가 batch 명령에서 받은 raw — "한국 brand 5선" 등), kicker (date · brand 수), meta (version · skill chain · mode)
- main grid: brand 1개당 card 1개
- card head: brand mark (CSS-generated initial chip 또는 DiceBear shapes if brand has known color) + 한글명 + id + wow rating
- frame-wrap: aspect-ratio 16:10 iframe (scale 50%로 200%×200% iframe rendering — 모바일은 100%)
- card foot: voice note 1줄 + tags chips + round-2 deltas ol
- footer summary: 모든 brand wow/lines/proof/round-2 핵심 1줄 테이블
- system-note: 적용된 skill 버전의 시스템 fix들 한 단락
2. CSS 스타일 가이드
- typography: Pretendard from jsdelivr (SIL OFL). 디스플레이는 본문 헤더에만 (
clamp(36px,4.4vw,56px) / weight 800 / letter-spacing -0.04em)
- 다크 surface (
#0b0d10) — gallery는 dark mode가 정석 (검토 환경 자체가 광원이 되도록)
- accent: gradient
linear-gradient(135deg, #7c5cfc 0%, #fa2e5f 50%, #04c584 100%) — Stripe-like
- card:
bg #13161b, border #252b35, hover border #7c5cfc + translateY -2px
- 반응형: ≥1100px 2-col grid, <1100px 1-col
3. iframe scaling
.frame-wrap { aspect-ratio: 16/10; background: #fff; overflow: hidden; position: relative; }
.frame-wrap iframe {
position: absolute; top: 0; left: 0;
width: 200%; height: 200%;
transform: scale(.5); transform-origin: top left;
border: 0;
}
.open-link {
position: absolute; top: 12px; right: 12px;
background: rgba(11,13,16,.7); color: #fff;
padding: 6px 12px; border-radius: 999px;
font-size: 11px; backdrop-filter: blur(8px);
}
200% × scale(.5)는 모바일 viewport에서도 데스크탑 layout 그대로 렌더하기 위함 (iframe 본인은 1280-1920px 가정).
4. 정적 vs 서버 모드
실행 절차
-
입력 검증: 디렉토리 list parsed, 각 디렉토리에 landing.html 존재 확인. 없으면 그 brand는 skip + 사용자에게 알림.
-
meta 수집: 각 brand 디렉토리에서:
experiment-meta.json 있으면 그대로 사용
- 없으면
DESIGN.md frontmatter에서 brand 추출, landing.html에서 <title> 추출 → minimal card
structure.json이 있으면 hero.type / cta.dominant_shape 정도를 tag로 추가
.live-inspect-proof.json 존재 → "live ✓" tag, raw_samples 수 표시
-
brand mark 생성: brand_color_hex가 있으면 색칩 div에 첫 글자. 없으면 회색 fallback.
-
gallery HTML 작성: 위 CSS + 카드 구조로 출력. <output-dir>/index.html에 write.
-
사용자 요약:
✓ Gallery 생성: <output-dir>/index.html
- 카드 N개 · wow 평균 X.X · live-inspect 통과 Y/N
- 서버 띄우는 법: cd <output-dir> && python3 -m http.server 8770
- 열기: http://localhost:8770/index.html
멀티턴 self-feedback 옵션 (v1.3.6 신설)
browser-harness 또는 mcp__playwright__* 가용 시, gallery 생성 후 gallery 자체에 self-critique 라운드:
- gallery index.html을 browser-harness로 열어 screenshot
- 각 brand 카드의 iframe rendering이 정상인지 (빈 화면 / 깨진 layout / 누락 자산) 시각 grading
- 발견된 문제 brand에 대해 issue.md 작성 (
<output-dir>/issues.md):
# Gallery issues — auto-detected via browser-harness
- toss: hero section reveals empty (IntersectionObserver fired but skill rule 10 safety net missing) — re-run with v1.3.6
- karrot: product card photo 3 fails to load (Loremflickr 503) — fallback to Picsum needed
- 사용자에게 issues.md 안내 + 자동 fix 진행 여부 묻기
안티패턴 (절대 금지)
- ❌ Brand 디렉토리 안의 자산을 gallery에 직접 복사 (iframe으로만 reference)
- ❌ Brand creative work 재구성 (각 brand의 own landing.html이 self-contained — gallery는 그 wrapper일 뿐)
- ❌ wow rating 임의 부여 (sub-agent의 honest assessment가 출처)
한 줄 요약
N개 brand experiment → 1개 index.html. iframe scaled, wow rating, round-2 deltas, system-fix summary. 재사용 무한.