1import * as mediaFiles from "#src/file-viewer/models/media-files.ts";
2import type { MediaFile } from "#src/file-viewer/models/media-files.ts";
3import "./clover-video.css";
4
5export interface Input {
6 id?: string;
7 file: MediaFile | string;
8 poster?: MediaFile | string;
9 header?: Marko.AttrTag<{ content: Marko.Body }>;
10 minimal?: boolean;
11 noFigure?: boolean;
12}
13
14<const/{ id, header, minimal, noFigure }=input>
15<const/file=(
16 typeof UNWRAP(input.file) === "object"
17 ? input.file
18 : UNWRAP(
19 mediaFiles.getByPath(input.file),
20 `No file ${JSON.stringify(input.file)}`,
21 )
22)>
23<const/poster=(
24 input.poster
25 ? typeof input.poster === "object"
26 ? input.poster
27 : UNWRAP(
28 mediaFiles.getByPath(input.poster),
29 `No file ${JSON.stringify(input.poster)}`,
30 )
31 : null
32)>
33
34<const/{ width, height }=mediaFiles.parseDimensions(file) ?? {
35 width: 1920,
36 height: 1080,
37}>
38<!-- which streaming manifests exist ("dash", "hls", or both). the player
39must only pick a backend whose manifest is actually present: dash can fail
40or lag behind hls for the same file. "pending" tells it to show a
41come-back-later note instead of silently failing -->
42<const/streams=(
43 [
44 derived.get(file, "dash.mpd") && "dash",
45 derived.get(file, "master.m3u8") && "hls",
46 ]
47 .filter(Boolean)
48 .join(",") || (file.pending ? "pending" : "none")
49)>
50
51<define/Inner>
52 <video
53 ...{ id }
54 class={ "clover-video": noFigure, minimal: noFigure && minimal }
55 data-src=file.path
56 data-streams=streams
57 poster=poster ? `/file${poster.path}` : null
58 width=width
59 height=height
60 />
61</define>
62
63<if=!noFigure>
64 <figure.clover-video class={ minimal }>
65 <if=!minimal>
66 <figcaption>
67 <if=header>
68 <${header.content}/>
69 </if>
70 <else>${file.basename}</else>
71 </figcaption>
72 </if>
73 <div.stack style=`aspect-ratio:${width}/${height}`>
74 <Inner/>
75 <noscript.fallback>
76 <h2>scripting disabled!</h2>
77 <p>
78 to play this video, JavaScript must be enabled in your browser. the
79 default video playback behavior is not enabled here as it results in a
80 worse experience on slower internet connections, and
81 <a href="http://caniuse.com/mpeg-dash">
82 MPEG-DASH streaming is not natively supported in any browser
83 </a>
84 without JavaScript.
85 </p>
86 <p>
87 since disabling JavaScript is not the default in any browser, you
88 likely wanted to download the raw video file anyways. those links are
89 available below, but note that you will need an AV1-compatible video
90 player, such as VLC Media Player or QuickTime Player (M3 chip or
91 newer)
92 </p>
93 </noscript>
94 </div>
95 </figure>
96</if>
97<else>
98 <Inner/>
99</else>
100
101client import "./clover-video.client.ts";
102
103import * as derived from "#src/file-viewer/models/derived.ts";
104import { UNWRAP, ASSERT } from "@clo/lib/assert";