arkaos 4.14.4 → 4.16.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,449 @@
1
+ ---
2
+ name: dev/animated-website
3
+ description: >
4
+ Convert an MP4 video into a luxury scroll-animated single-file website:
5
+ extracts frames to optimized WebP (desktop + mobile), then builds a
6
+ scroll-driven canvas engine with cinematic dwell pacing, ambient particles,
7
+ film grain, letter-split hero, glass morphism cards, and parallax gallery.
8
+ TRIGGER: "animated website", "scroll animation", "video to website",
9
+ "Apple-style page", "site com scroll do vídeo", "transforma este vídeo num
10
+ site", "frame animation", "/dev animated-website". SKIP: embedding a plain
11
+ video player -> just use <video>; regular animated site WITHOUT a video
12
+ source -> frontend-design skill; video editing/production -> content/video-produce.
13
+ allowed-tools: [Read, Write, Edit, Bash, Grep, Glob, Agent, WebFetch]
14
+ ---
15
+
16
+ # Animated Website Generator
17
+
18
+ > **ArkaOS frontend mandate:** this is UI work under `excellence-mandate` —
19
+ > load the frontend design skills (frontend-design, ui-ux-pro-max, project
20
+ > design system) at maximum effort, emit the `[arka:design]` evidence marker
21
+ > before editing UI files, and pass visual review against a named benchmark
22
+ > (Apple product pages are the default bar for this skill).
23
+
24
+ Convert video files into scroll-animated websites with a luxury, cinematic aesthetic. The user provides an MP4 video and a concept brief. You extract frames, optimize for web delivery, and generate a complete website where scrolling plays the video frame-by-frame on a canvas element — with rich overlay text, ambient effects, and gallery sections that elevate it beyond a simple scroll player.
25
+
26
+ The design language draws from high-end real estate, product launches, and editorial showcases: warm dark palettes, serif/sans-serif type pairing, ambient particles, film grain texture, glass morphism cards, and a scroll-dwell engine that creates natural pacing through content sections.
27
+
28
+ ---
29
+
30
+ ## When This Skill Applies
31
+
32
+ **This skill IS for:**
33
+ - Converting an MP4 video into a scroll-driven animated website
34
+ - Luxury showcase pages (real estate, architecture, product, portfolio)
35
+ - Apple product page-style frame sequences (scroll to play)
36
+ - Any "video → interactive scroll experience" request
37
+
38
+ **This skill is NOT for:**
39
+ - Embedding a video player on a page (just use `<video>`)
40
+ - Converting video to GIF or animated WebP
41
+ - Building a regular website without video-based scroll animation
42
+ - CSS-only scroll animations (use the `frontend-design` skill instead)
43
+
44
+ **Redirect:** If the user wants a regular animated website WITHOUT a video source, use the `frontend-design` skill.
45
+
46
+ ---
47
+
48
+ ## Input: What You Need From the User
49
+
50
+ **Required:**
51
+ 1. **An MP4 video file** — absolute path to the source video
52
+ 2. **Website concept** — what the site is about (product, brand, property, portfolio, etc.)
53
+
54
+ **Optional (skill handles defaults if not provided):**
55
+ - Target frame count (default: auto-calculated from video duration)
56
+ - Brand colors (default: warm-dark luxury palette)
57
+ - Section copy (headlines, body text, CTAs)
58
+ - Brand name and tagline
59
+
60
+ If the user gives just a video path and a vague concept, ask ONE clarifying question about the content direction, then proceed.
61
+
62
+ ---
63
+
64
+ ## Process
65
+
66
+ ### Step 1: Analyze the Video
67
+
68
+ Probe the video to understand what you're working with:
69
+
70
+ ```bash
71
+ ffprobe -v quiet -print_format json -show_format -show_streams "/path/to/video.mp4"
72
+ ```
73
+
74
+ Parse and present:
75
+
76
+ ```
77
+ VIDEO ANALYSIS:
78
+ Duration: 12.4s
79
+ Resolution: 3840x2160 (4K)
80
+ Frame Rate: 30fps
81
+ Total Frames: 372
82
+ Codec: H.264
83
+ ```
84
+
85
+ Then recommend frame count:
86
+
87
+ | Video Duration | Recommended Frames | Scroll Height |
88
+ |---------------|-------------------|---------------|
89
+ | 0-5s | 60-90 | 400vh |
90
+ | 5-15s | 100-150 | 650vh |
91
+ | 15-30s | 150-200 | 800vh |
92
+ | 30s+ | Cap at 200 | 900vh |
93
+
94
+ **Get user confirmation before extracting.** Say: "I recommend extracting {N} frames. Sound good, or want to adjust?"
95
+
96
+ ### Step 2: Extract and Optimize Frames
97
+
98
+ Run the extraction script bundled with this skill (`scripts/extract_frames.py`, relative to this SKILL.md):
99
+
100
+ ```bash
101
+ python3 scripts/extract_frames.py \
102
+ --input "/path/to/video.mp4" \
103
+ --output "animated-sites/{slug}/frames" \
104
+ --frames {N} \
105
+ --quality 80
106
+ ```
107
+
108
+ Set `--output` to a folder inside the current working directory.
109
+
110
+ The script produces:
111
+ - `frames/desktop/` — 1920x1080 WebP frames
112
+ - `frames/mobile/` — 960x540 WebP frames
113
+ - `frames/manifest.json` — metadata (counts, sizes, scroll height)
114
+
115
+ Show the manifest summary to the user. If payload exceeds budget (>10MB desktop, >5MB mobile), recommend `--quality 60` or fewer frames.
116
+
117
+ ### Step 3: Gather Content
118
+
119
+ Based on the user's concept, prepare content for 6 scroll-text sections. These overlay the video at different scroll positions, creating a narrative experience. The sections are:
120
+
121
+ 1. **Hero** — Property/product name, tagline, key stats
122
+ 2. **Vision** — A quote or aspirational statement about the subject
123
+ 3. **Details** — Key specifications or features (with icon list)
124
+ 4. **Grid** — 4-6 amenities/features in a glass grid layout
125
+ 5. **Context** — Location, availability, or background info
126
+ 6. **CTA** — Call to action with buttons and contact info
127
+
128
+ If the user provides copy, use it. If not, generate content that fits the concept. The content should feel editorial and refined — short sentences, evocative language.
129
+
130
+ ### Step 4: Build the Website
131
+
132
+ Generate a complete single-file HTML page using the design system below. Save to: `animated-sites/{slug}/index.html`
133
+
134
+ **Adapt the content and branding to the concept** — the design patterns stay consistent but the palette, copy, and section content should fit the subject matter. A tech product might use cooler blues, a restaurant warmer golds, a real estate listing the warm-neutral default.
135
+
136
+ ### Step 5: Serve and Preview
137
+
138
+ ```bash
139
+ cd "animated-sites/{slug}"
140
+ python3 -m http.server 8080
141
+ ```
142
+
143
+ Then open `http://localhost:8080/index.html` in the browser and take screenshots at different scroll positions to verify.
144
+
145
+ Common iteration requests:
146
+ - "Slower scroll" → increase animation-section height (650vh → 900vh)
147
+ - "Faster scroll" → decrease height (650vh → 400vh)
148
+ - "Smoother animation" → decrease LERP_FACTOR (0.09 → 0.05)
149
+ - "More responsive" → increase LERP_FACTOR (0.09 → 0.15)
150
+ - "Change text" → edit the scroll-text overlay content
151
+ - "Different colors" → update CSS custom properties in `:root`
152
+
153
+ ---
154
+
155
+ ## Design System
156
+
157
+ The visual language is warm, dark, and cinematic. Every element serves the animation — surrounding effects (grain, particles, vignette) add depth without competing with the video frames.
158
+
159
+ ### Color Palette (CSS Custom Properties)
160
+
161
+ ```css
162
+ :root {
163
+ --concrete: #d4cfc8; /* muted warm gray */
164
+ --concrete-dim: #9e9890; /* secondary text */
165
+ --stone: #706050; /* decorative accents */
166
+ --charcoal: #1a1816; /* card backgrounds */
167
+ --ink: #0e0d0c; /* page background */
168
+ --warm-white: #f4f0ea; /* primary text */
169
+ --warm-white-dim: #c8c0b4; /* emphasized secondary */
170
+ --accent-blue: #4a6aff; /* accent color - adapt per brand */
171
+ --accent-blue-glow: rgba(74, 106, 255, 0.35);
172
+ --accent-blue-soft: rgba(74, 106, 255, 0.08);
173
+ --sunset-pink: #d4a0b0; /* secondary accent */
174
+ --gold-warm: #c89848; /* tertiary accent */
175
+ --heading: 'Playfair Display', 'Georgia', serif;
176
+ --body: 'DM Sans', -apple-system, BlinkMacSystemFont, sans-serif;
177
+ }
178
+ ```
179
+
180
+ Adapt the `--accent-blue` family for different brands. The warm-dark base (`--ink`, `--warm-white`) stays consistent — it makes the video frames pop and creates the luxury atmosphere.
181
+
182
+ ### Typography
183
+
184
+ - **Headings:** Playfair Display — weight 300 for elegance, italic for emphasis
185
+ - **Body:** DM Sans — weight 300-500, generous letter-spacing
186
+ - **Labels:** DM Sans, 8-9px, weight 500, 0.25-0.35em letter-spacing, uppercase
187
+ - **Hero titles:** clamp(42px, 5.5vw, 76px) — big but light weight
188
+
189
+ Load from Google Fonts:
190
+ ```html
191
+ <link href="https://fonts.googleapis.com/css2?family=DM+Sans:ital,wght@0,300;0,400;0,500;0,600;1,300;1,400&family=Playfair+Display:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400&display=swap" rel="stylesheet">
192
+ ```
193
+
194
+ ### Layer Stack (z-index)
195
+
196
+ The site layers multiple visual effects. Here's the stacking order:
197
+
198
+ | Z-Index | Element | Purpose |
199
+ |---------|---------|---------|
200
+ | 9999 | Loader | Branded loading screen with progress bar |
201
+ | 9998 | Cursor dot | Custom cursor inner dot (mix-blend-mode: difference) |
202
+ | 9997 | Cursor ring | Custom cursor outer ring (expands on hover) |
203
+ | 100 | Film grain | SVG noise overlay at 3.5% opacity |
204
+ | 99 | Vignette | Radial gradient darkening edges |
205
+ | 50 | Chapter markers | Fixed right-side navigation dots |
206
+ | 15 | Particles | Ambient floating particles canvas |
207
+ | 10 | Scroll text | Content overlays during animation |
208
+ | 5 | Tint overlay | Dynamic color wash per section |
209
+ | 1 | Canvas overlays | Left gradient + bottom gradient for text readability |
210
+ | 0 | Video canvas | The scroll-driven frame animation |
211
+
212
+ ### Ambient Effects
213
+
214
+ These create the cinematic atmosphere. All are pointer-events: none and purely decorative.
215
+
216
+ **Film Grain:** SVG feTurbulence fractalNoise, 256px tile, opacity 0.035. Gives the site a filmic texture.
217
+
218
+ **Vignette:** Radial gradient from transparent (center 50%) to rgba(14,13,12,0.45) at edges. Draws focus to center.
219
+
220
+ **Ambient Particles:** Fixed canvas, ~40 small dots (0.3-1.8px), slow random drift, warm-white at 5-35% opacity. Creates a living, breathing feel. Wrap at edges so they float continuously.
221
+
222
+ **Dynamic Tint:** Canvas overlay that shifts hue based on current scroll section. Subtle (6-4% opacity) gradient from accent-blue to sunset-pink. Makes each section feel distinct.
223
+
224
+ **Custom Cursor (desktop only):** Two-part cursor: a 6px dot with mix-blend-mode: difference (always visible against any background) and a 36px ring that trails the dot with LERP. Ring expands to 56px on hover over interactive elements and gains accent-blue glow. Hide on mobile.
225
+
226
+ ### Scroll Dwell Engine
227
+
228
+ This is what makes the scroll feel magical instead of mechanical. Rather than mapping scroll position linearly to frames, the dwell engine creates "almost stops" at each content section — the scroll slows down there, giving users time to read, then speeds up between sections.
229
+
230
+ **How it works:**
231
+ 1. Define dwell centers — the scroll positions where content appears (e.g., 0.065, 0.21, 0.365, 0.525, 0.685, 0.89)
232
+ 2. At each center, a Gaussian density function peaks — meaning more scroll distance is consumed per unit of effective progress
233
+ 3. Build a cumulative integral lookup table (forward mapping)
234
+ 4. Invert it for the actual remap function (scroll position → effective progress)
235
+
236
+ The dwell centers should align with the `data-show-at` values of scroll-text sections. With 6 sections, space them roughly evenly across 0-1 but offset from the edges.
237
+
238
+ Parameters to tune:
239
+ - `DWELL_WIDTH` (0.045): How wide the slow zone is. Smaller = tighter pause.
240
+ - `DWELL_PEAK` (3.5): How much slower the scroll feels at dwell points. Higher = more dramatic pause.
241
+ - `REMAP_N` (2000): Resolution of the lookup table. 2000 is smooth enough.
242
+
243
+ ### Scroll Text Overlays
244
+
245
+ Six sections that appear and disappear at specific scroll positions. Each has its own layout and style:
246
+
247
+ 1. **Hero** (positioned left, 6% from edge): Property/product name with letter-split animation, tagline, price/key metric. Has a glass stat bar at bottom with 4-5 key numbers.
248
+
249
+ 2. **Vision** (positioned left): Opening quotation mark as decorative element, italic serif quote, divider line, attribution.
250
+
251
+ 3. **Details** (positioned left): Overline label, serif title, body text, feature list with icon items and subtle borders.
252
+
253
+ 4. **Grid** (positioned left): Overline label, 2-column glass grid of 6 amenity/feature cells with icons and descriptions.
254
+
255
+ 5. **Context** (positioned left): Overline label, serif title, body text, distance/detail list with dotted connecting lines.
256
+
257
+ 6. **CTA** (centered): Large serif title with italic emphasis, subtitle, two buttons (primary filled, secondary outline), and agent/contact card.
258
+
259
+ Each section fades in with blur(6px→0) and translateX(-20px→0) transitions. The `.visible` class is toggled based on scroll progress matching the `data-show-at` / `data-hide-at` attributes.
260
+
261
+ ### Glass Morphism Cards
262
+
263
+ Used for stat bars and amenity grids:
264
+ - Background: rgba(244, 240, 234, 0.03)
265
+ - backdrop-filter: blur(20px)
266
+ - Border: 1px solid rgba(244, 240, 234, 0.06)
267
+ - On hover: background brightens to 0.06, border gains accent-blue tint
268
+
269
+ ### Chapter Markers
270
+
271
+ Fixed right-side vertical navigation showing 6 dots connected by lines. The active dot gets accent-blue glow and the connecting line fills with progress as you scroll through the section. Dots can have labels that appear on hover.
272
+
273
+ ### Gallery Section
274
+
275
+ Below the scroll animation, a masonry-ish grid of frames from the video. Uses IntersectionObserver for reveal animations and requestAnimationFrame-based parallax transforms (data-parallax attribute with positive/negative px values).
276
+
277
+ Grid layout: `grid-template-columns: repeat(3, 1fr)` with some items spanning 2 rows via `.tall` class. Images have subtle hover zoom (scale 1.03) with overflow hidden.
278
+
279
+ Pick 6-7 evenly spaced frames from the video for gallery images.
280
+
281
+ ### Branded Loader
282
+
283
+ Not just a progress bar — a branded experience:
284
+ - Centered brand mark in uppercase letter-spaced heading font
285
+ - Decorative lines above and below
286
+ - Thin 140px progress bar with gradient fill (accent-blue → sunset-pink)
287
+ - Percentage counter below
288
+ - Exits with opacity 0 + blur(8px) transition
289
+
290
+ ### Footer
291
+
292
+ Minimal: brand name in heading font, legal line in small body text, dark background slightly lighter than ink.
293
+
294
+ ---
295
+
296
+ ## Code Architecture
297
+
298
+ The entire site is a single HTML file. Here's the structural order:
299
+
300
+ ```
301
+ HTML:
302
+ 1. Google Fonts link
303
+ 2. <style> with all CSS
304
+ 3. Custom cursor divs (#cursor-dot, #cursor-ring)
305
+ 4. Film grain overlay div
306
+ 5. Vignette overlay div
307
+ 6. Particles canvas (fixed)
308
+ 7. Loader (fixed, z-9999)
309
+ 8. Chapter markers (fixed right)
310
+ 9. Animation section (relative, 650vh)
311
+ - Canvas container (sticky)
312
+ - Main canvas
313
+ - Left gradient overlay
314
+ - Bottom gradient overlay
315
+ - Tint overlay
316
+ - 6 scroll-text overlays (fixed, toggled by JS)
317
+ 10. Gallery section
318
+ 11. Footer
319
+ 12. <script> with all JS
320
+
321
+ JS order:
322
+ 1. Custom cursor tracking + ring LERP
323
+ 2. Particle system init + animation loop
324
+ 3. Letter-split animation (data-split attribute)
325
+ 4. Scroll dwell/remap engine (LUT construction)
326
+ 5. Frame loading (critical first, then batches)
327
+ 6. Scroll animation loop (remap → LERP → drawFrame)
328
+ 7. Scroll-text visibility toggling
329
+ 8. Chapter marker updates
330
+ 9. Tint overlay updates
331
+ 10. Gallery IntersectionObserver + parallax
332
+ 11. Stat counter animation
333
+ 12. Init: load frames → hide loader → start animation
334
+ ```
335
+
336
+ ### Key JavaScript Patterns
337
+
338
+ **Frame loading with progressive enhancement:**
339
+ ```javascript
340
+ // Critical frames first (evenly spaced), then batches
341
+ // Use createImageBitmap for off-thread decode when available
342
+ // Show first frame immediately after critical load
343
+ ```
344
+
345
+ **Scroll-to-frame with dwell remap:**
346
+ ```javascript
347
+ function getScrollProgress() {
348
+ const rect = section.getBoundingClientRect();
349
+ return Math.max(0, Math.min(1, -rect.top / (rect.height - window.innerHeight)));
350
+ }
351
+
352
+ function animate() {
353
+ const rawProgress = getScrollProgress();
354
+ const remapped = remapProgress(rawProgress); // dwell engine
355
+ targetFrame = Math.floor(remapped * (FRAME_COUNT - 1));
356
+ currentFrame += (targetFrame - currentFrame) * LERP_FACTOR;
357
+ drawFrame(Math.round(currentFrame));
358
+ // Also update scroll-text visibility, chapter markers, tint
359
+ requestAnimationFrame(animate);
360
+ }
361
+ ```
362
+
363
+ **Stat counter animation:**
364
+ ```javascript
365
+ // When stat-bar becomes visible, animate numbers from 0 to target
366
+ // Use ease-out cubic easing over ~1.5s
367
+ // Parse target from data-target attribute, handle commas/units
368
+ ```
369
+
370
+ ---
371
+
372
+ ## Adapting for Different Concepts
373
+
374
+ The design system is flexible. Here's how to adapt it:
375
+
376
+ **Real Estate:** Default palette works perfectly. Use property name as hero title, price and specs in stat bar, architecture details, amenity grid, location distances, viewing CTA.
377
+
378
+ **Tech Product:** Shift accent to cooler blue (#2563eb) or electric violet (#7c3aed). Hero has product name + tagline, stat bar shows key specs (battery, weight, price), Details lists tech specs, Grid shows features, CTA is "Pre-order" or "Learn More".
379
+
380
+ **Portfolio/Creative:** Use gold-warm (#c89848) as accent. Hero has creator name + discipline, Vision quotes an artistic statement, Details shows notable works, Grid shows services/capabilities, CTA is "Get in Touch".
381
+
382
+ **Restaurant/Hospitality:** Warm accent (#c89848 or deep burgundy). Hero is venue name, Vision is a chef quote, Details is cuisine philosophy, Grid is menu highlights or experiences, Context is location/hours.
383
+
384
+ **Automotive:** Keep accent-blue or shift to silver (#a8a8a8). Hero is vehicle name + starting price, stat bar shows 0-60/HP/range, Details is engineering highlights.
385
+
386
+ In all cases, the 6-section structure, ambient effects, scroll-dwell engine, and glass morphism cards remain the same — they create the luxury feel regardless of content.
387
+
388
+ ---
389
+
390
+ ## Quality Checklist
391
+
392
+ Before showing the site to the user, verify:
393
+
394
+ - [ ] **Smooth at 60fps** — no jank or frame drops during scroll
395
+ - [ ] **First frame visible in <1s** — progressive loading works
396
+ - [ ] **Loading bar accurate** — gradient fill, percentage counter updates
397
+ - [ ] **Desktop payload <10MB** — check manifest.json
398
+ - [ ] **Mobile payload <5MB** — check manifest.json
399
+ - [ ] **Reduced motion handled** — static first frame when prefers-reduced-motion
400
+ - [ ] **No blank frames** — nearest-neighbor fallback fills gaps
401
+ - [ ] **Responsive** — canvas scales on resize, mobile layout works
402
+ - [ ] **Custom cursor works on desktop** — dot tracks instantly, ring trails
403
+ - [ ] **Particles animate** — subtle floating dots visible against dark bg
404
+ - [ ] **Scroll text appears/disappears** — 6 sections at correct scroll positions
405
+ - [ ] **Letter-split hero animates** — characters appear sequentially
406
+ - [ ] **Glass stat bar readable** — blur backdrop works, numbers visible
407
+ - [ ] **Gallery loads** — images from frames directory, parallax on scroll
408
+ - [ ] **Dwell engine feels natural** — scroll slows at content, speeds between
409
+ - [ ] **Chapter markers update** — active dot highlighted, progress lines fill
410
+
411
+ ---
412
+
413
+ ## Output Format
414
+
415
+ ```
416
+ animated-sites/{slug}/
417
+ ├── frames/
418
+ │ ├── desktop/ # 1920x1080 WebP
419
+ │ │ ├── frame-0001.webp
420
+ │ │ └── ...
421
+ │ ├── mobile/ # 960x540 WebP
422
+ │ │ ├── frame-0001.webp
423
+ │ │ └── ...
424
+ │ └── manifest.json # Frame metadata
425
+ └── index.html # Complete luxury scroll site
426
+ ```
427
+
428
+ To view: `cd` into the output directory and run `python3 -m http.server 8080`, then open `localhost:8080`.
429
+
430
+ ---
431
+
432
+ ## Troubleshooting
433
+
434
+ | Issue | Fix |
435
+ |-------|-----|
436
+ | FFmpeg not found | `brew install ffmpeg` |
437
+ | No libwebp support | `brew reinstall ffmpeg` (includes libwebp by default) |
438
+ | Frames too large (>10MB) | Lower quality: `--quality 60`. Reduce count: `--frames 90` |
439
+ | Animation stutters | Reduce frame count. Check DPR cap is 2. Decrease particles. |
440
+ | White flash between frames | Nearest-frame fallback not finding frames. Check extraction. |
441
+ | Canvas blank on mobile | Verify mobile frames exist. Check FRAME_DIR path switch. |
442
+ | Loading bar stuck | A frame 404'd. Check browser console. Verify frame paths. |
443
+ | Scroll too fast/slow | Adjust animation-section height. 650vh = default. |
444
+ | Dwell feels too sticky | Decrease DWELL_PEAK (3.5 → 2.5) or increase DWELL_WIDTH |
445
+ | Particles too visible | Decrease particles-canvas opacity (0.4 → 0.2) |
446
+ | Custom cursor jittery | Increase ring LERP factor (0.15 → 0.2) |
447
+ | Glass blur not working | Safari needs -webkit-backdrop-filter. Already included in CSS. |
448
+ | CORS error locally | Serve with `python3 -m http.server 8080`. Don't double-click HTML. |
449
+ | Fonts not loading | Check Google Fonts link. Fallback fonts in CSS vars handle it. |