OverviewFilesCommitsIssuesDocsReleasesPeers

folio commits / f473345

Add HLS adaptive video streaming design
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
f473345b0e759560a0eb71ce0221918b26f22b84
by plankatron <fleeky@gmail.com> · 2026-03-17T21:36:59.000Z

Changed files (1) +64 -0

docs/plans/2026-03-17-hls-adaptive-video-design.md +64 -0
……@@ -0,0 +1,64 @@
1# HLS Adaptive Video Streaming — Design
2
3## Overview
4
5Add adaptive bitrate streaming to the folio portfolio template using HLS. Videos are segmented into multiple quality levels during preprocessing. The hls.js library handles playback with automatic quality switching based on bandwidth.
6
7## Preprocessing
8
9For each video in `videos/<collection>/`, ffmpeg generates HLS segments at up to 3 quality levels:
10
11- **480p** — 854x480, 1Mbps, baseline profile
12- **720p** — 1280x720, 2.5Mbps, main profile
13- **1080p** — 1920x1080, 5Mbps, high profile (only if source >= 1080p)
14
15No upscaling — only generates levels the source resolution supports.
16
17Segment length: 6 seconds.
18
19### Output structure
20
21```
22videos/<collection>/
23├── video.mp4 # original (untouched)
24├── video/
25│ ├── master.m3u8 # master playlist
26│ ├── 480p.m3u8 # segment playlist
27│ ├── 480p_000.ts
28│ ├── 720p.m3u8
29│ ├── 720p_000.ts
30│ ├── 1080p.m3u8
31│ └── 1080p_000.ts
32└── thumbs/
33 └── video.jpg # poster frame
34```
35
36## Manifest
37
38Video items gain an `hls` field pointing to the master playlist:
39
40```json
41{
42 "type": "video",
43 "name": "video.mp4",
44 "full": "videos/collection/video.mp4",
45 "hls": "videos/collection/video/master.m3u8",
46 "thumb": "videos/collection/thumbs/video.jpg",
47 "duration": 368.7
48}
49```
50
51## Frontend
52
53- **hls.js** vendored at `vendor/hls.min.js` (~60KB gzipped, MIT license)
54- Player checks `item.hls`: if present, uses hls.js for adaptive playback
55- Safari gets native HLS (no hls.js needed)
56- Fallback: if no `hls` field, plays `item.full` as plain MP4
57- Quality indicator in controls showing current level (auto/480p/720p/1080p)
58
59## Backwards compatibility
60
61- Original MP4 kept alongside HLS segments
62- Videos without HLS segments still work (plain MP4 playback)
63- Images completely unaffected
64- All existing player controls (seek, skip, theater, buffer) unchanged