hyperframes 0.6.109 → 0.6.110

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.
package/dist/cli.js CHANGED
@@ -50,7 +50,7 @@ var VERSION;
50
50
  var init_version = __esm({
51
51
  "src/version.ts"() {
52
52
  "use strict";
53
- VERSION = true ? "0.6.109" : "0.0.0-dev";
53
+ VERSION = true ? "0.6.110" : "0.0.0-dev";
54
54
  }
55
55
  });
56
56
 
@@ -74891,10 +74891,17 @@ function findOnPath2(name) {
74891
74891
  return void 0;
74892
74892
  }
74893
74893
  }
74894
+ function findInCommonDirs(name) {
74895
+ for (const dir of COMMON_BIN_DIRS) {
74896
+ const candidate = `${dir}/${name}`;
74897
+ if (existsSync19(candidate)) return candidate;
74898
+ }
74899
+ return void 0;
74900
+ }
74894
74901
  function findConfiguredBinary(envName, binaryName) {
74895
74902
  const configured = process.env[envName]?.trim();
74896
74903
  if (configured) return existsSync19(configured) ? resolve10(configured) : void 0;
74897
- return findOnPath2(binaryName);
74904
+ return findOnPath2(binaryName) ?? findInCommonDirs(binaryName);
74898
74905
  }
74899
74906
  function findFFmpeg() {
74900
74907
  return findConfiguredBinary(FFMPEG_PATH_ENV2, "ffmpeg");
@@ -74914,12 +74921,13 @@ function getFFmpegInstallHint() {
74914
74921
  return "https://ffmpeg.org/download.html";
74915
74922
  }
74916
74923
  }
74917
- var FFMPEG_PATH_ENV2, FFPROBE_PATH_ENV2;
74924
+ var FFMPEG_PATH_ENV2, FFPROBE_PATH_ENV2, COMMON_BIN_DIRS;
74918
74925
  var init_ffmpeg = __esm({
74919
74926
  "src/browser/ffmpeg.ts"() {
74920
74927
  "use strict";
74921
74928
  FFMPEG_PATH_ENV2 = "HYPERFRAMES_FFMPEG_PATH";
74922
74929
  FFPROBE_PATH_ENV2 = "HYPERFRAMES_FFPROBE_PATH";
74930
+ COMMON_BIN_DIRS = process.platform === "win32" ? [] : ["/opt/homebrew/bin", "/usr/local/bin", "/usr/bin", "/bin", "/snap/bin"];
74923
74931
  }
74924
74932
  });
74925
74933
 
@@ -101029,20 +101037,25 @@ var init_init = __esm({
101029
101037
  console.error(c.error(`Directory already exists and is not empty: ${name2}`));
101030
101038
  process.exit(1);
101031
101039
  }
101032
- mkdirSync33(destDir2, { recursive: true });
101033
- let localVideoName2;
101034
- let videoDuration2;
101035
- let sourceFilePath2;
101036
101040
  if (videoFlag && audioFlag) {
101037
101041
  console.error(c.error("Cannot use --video and --audio together"));
101038
101042
  process.exit(1);
101039
101043
  }
101040
- if (videoFlag) {
101041
- const videoPath = resolve31(videoFlag);
101042
- if (!existsSync54(videoPath)) {
101043
- console.error(c.error(`Video file not found: ${videoFlag}`));
101044
- process.exit(1);
101045
- }
101044
+ const videoPath = videoFlag ? resolve31(videoFlag) : void 0;
101045
+ if (videoPath && !existsSync54(videoPath)) {
101046
+ console.error(c.error(`Video file not found: ${videoFlag}`));
101047
+ process.exit(1);
101048
+ }
101049
+ const audioPath = audioFlag ? resolve31(audioFlag) : void 0;
101050
+ if (audioPath && !existsSync54(audioPath)) {
101051
+ console.error(c.error(`Audio file not found: ${audioFlag}`));
101052
+ process.exit(1);
101053
+ }
101054
+ mkdirSync33(destDir2, { recursive: true });
101055
+ let localVideoName2;
101056
+ let videoDuration2;
101057
+ let sourceFilePath2;
101058
+ if (videoPath) {
101046
101059
  sourceFilePath2 = videoPath;
101047
101060
  const result = await handleVideoFile(videoPath, destDir2, false);
101048
101061
  localVideoName2 = result.localVideoName;
@@ -101051,12 +101064,7 @@ var init_init = __esm({
101051
101064
  `Video: ${result.meta.width}x${result.meta.height}, ${result.meta.durationSeconds.toFixed(1)}s`
101052
101065
  );
101053
101066
  }
101054
- if (audioFlag) {
101055
- const audioPath = resolve31(audioFlag);
101056
- if (!existsSync54(audioPath)) {
101057
- console.error(c.error(`Audio file not found: ${audioFlag}`));
101058
- process.exit(1);
101059
- }
101067
+ if (audioPath) {
101060
101068
  sourceFilePath2 = audioPath;
101061
101069
  copyFileSync6(audioPath, resolve31(destDir2, basename10(audioPath)));
101062
101070
  console.log(`Audio: ${basename10(audioPath)}`);
@@ -149259,8 +149267,8 @@ var init_snapshot = __esm({
149259
149267
  init_ffmpeg();
149260
149268
  FFMPEG_EXTRACT_TIMEOUT_MS = 3e4;
149261
149269
  examples24 = [
149262
- ["Capture 5 key frames from a composition", "snapshot captures/stripe"],
149263
- ["Capture 10 evenly-spaced frames", "snapshot captures/stripe --frames 10"]
149270
+ ["Capture 5 key frames from a composition", "snapshot capture"],
149271
+ ["Capture 10 evenly-spaced frames", "snapshot capture --frames 10"]
149264
149272
  ];
149265
149273
  snapshot_default = defineCommand({
149266
149274
  meta: {
@@ -153115,8 +153123,8 @@ var init_capture2 = __esm({
153115
153123
  "use strict";
153116
153124
  init_dist();
153117
153125
  examples25 = [
153118
- ["Capture a website", "hyperframes capture https://stripe.com"],
153119
- ["Capture to a specific directory", "hyperframes capture https://linear.app -o linear-video"],
153126
+ ["Capture a website into ./capture/", "hyperframes capture https://stripe.com"],
153127
+ ["Capture to a different directory", "hyperframes capture https://linear.app -o linear-video"],
153120
153128
  ["JSON output for AI agents", "hyperframes capture https://example.com --json"],
153121
153129
  [
153122
153130
  "Pull a video from the captured manifest by index",
@@ -153140,7 +153148,7 @@ var init_capture2 = __esm({
153140
153148
  },
153141
153149
  output: {
153142
153150
  type: "string",
153143
- description: "Output directory name",
153151
+ description: "Output directory name (default: ./capture, then ./capture-2/, ./capture-3/, \u2026)",
153144
153152
  alias: "o"
153145
153153
  },
153146
153154
  "skip-assets": {
@@ -153179,6 +153187,7 @@ var init_capture2 = __esm({
153179
153187
  default: false
153180
153188
  }
153181
153189
  },
153190
+ // fallow-ignore-next-line complexity
153182
153191
  async run({ args }) {
153183
153192
  if (args.video) {
153184
153193
  const { runVideoMode: runVideoMode2 } = await Promise.resolve().then(() => (init_video(), video_exports));
@@ -153203,17 +153212,30 @@ var init_capture2 = __esm({
153203
153212
  console.error(`Invalid URL: ${url}`);
153204
153213
  process.exit(1);
153205
153214
  }
153206
- let outputName = args.output;
153207
- if (!outputName) {
153208
- const hostname = new URL(url).hostname.replace(/^www\./, "");
153209
- outputName = `captures/${hostname.replace(/\./g, "-")}`;
153215
+ const isDefaultOutput = !args.output;
153216
+ let outputName = args.output ?? "capture";
153217
+ let outputDir = resolve52(outputName);
153218
+ if (isDefaultOutput) {
153219
+ const { existsSync: existsSync92 } = await import("fs");
153220
+ let n2 = 2;
153221
+ while (existsSync92(outputDir) && n2 < 100) {
153222
+ outputName = `capture-${n2}`;
153223
+ outputDir = resolve52(outputName);
153224
+ n2++;
153225
+ }
153226
+ if (existsSync92(outputDir)) {
153227
+ console.error(`./capture-{2..99} are all taken. Pass -o <name> to pick a directory.`);
153228
+ process.exit(1);
153229
+ }
153210
153230
  }
153211
- const outputDir = resolve52(outputName);
153212
153231
  const isJson = args.json;
153213
153232
  if (!isJson) {
153214
153233
  const { c: c3 } = await Promise.resolve().then(() => (init_colors(), colors_exports));
153215
153234
  console.log();
153216
153235
  console.log(c3.dim("\u25C6") + " Capturing " + c3.bold(url));
153236
+ if (isDefaultOutput && outputName !== "capture") {
153237
+ console.log(` ${c3.dim(`(./capture/ exists; writing to ./${outputName}/)`)}`);
153238
+ }
153217
153239
  console.log();
153218
153240
  }
153219
153241
  const { captureWebsite: captureWebsite2 } = await Promise.resolve().then(() => (init_capture(), capture_exports));
@@ -0,0 +1,418 @@
1
+ var ue=Object.defineProperty;var ce=(n,t,e)=>t in n?ue(n,t,{enumerable:!0,configurable:!0,writable:!0,value:e}):n[t]=e;var h=(n,t,e)=>ce(n,typeof t!="symbol"?t+"":t,e);function pe(n){return n.hasRuntime||n.runtimeInjected?!1:!!(n.hasNestedCompositions||n.hasTimelines&&n.attempts>=5)}function D(n){return typeof n=="object"&&n!==null}function me(n){return D(n)&&typeof n.getDuration=="function"}function fe(n){return D(n)&&typeof n.duration=="function"&&typeof n.time=="function"&&typeof n.seek=="function"&&typeof n.play=="function"&&typeof n.pause=="function"}const _e="https://cdn.jsdelivr.net/npm/@hyperframes/core/dist/hyperframe.runtime.iife.js";function F(n){if(n===null)return null;const t=Number.parseInt(n,10);return Number.isFinite(t)&&t>0?t:null}function ge(n){const t=(n==null?void 0:n.querySelector("[data-composition-id][data-width][data-height]"))??(n==null?void 0:n.querySelector("[data-width][data-height]"));if(!t)return null;const e=F(t.getAttribute("data-width")),i=F(t.getAttribute("data-height"));return e!==null&&i!==null?{width:e,height:i}:null}class be{constructor(t,e){h(this,"_interval",null);h(this,"_runtimeInjected",!1);this._iframe=t,this._callbacks=e}get runtimeInjected(){return this._runtimeInjected}start(){this.stop(),this._runtimeInjected=!1;let t=0;this._interval=setInterval(()=>{var e;t++;try{const i=this._iframe.contentWindow;if(!i)return;const r=!!(i.__hf||i.__player),s=!!(i.__timelines&&Object.keys(i.__timelines).length>0),a=!!((e=this._iframe.contentDocument)!=null&&e.querySelector("[data-composition-src]"));if(pe({hasRuntime:r,hasTimelines:s,hasNestedCompositions:a,runtimeInjected:this._runtimeInjected,attempts:t})){this._injectRuntime();return}if(this._runtimeInjected&&!r)return;const l=this._resolvePlaybackDurationAdapter(i);if(l&&l.getDuration()>0){this.stop();const p=ge(this._iframe.contentDocument);this._callbacks.onReady({duration:l.getDuration(),adapter:l,compositionSize:p});return}}catch{}t>=40&&(this.stop(),this._callbacks.onError("Composition timeline not found after 8s"))},200)}stop(){this._interval!==null&&(clearInterval(this._interval),this._interval=null)}resolveDirectTimelineAdapter(){try{const t=this._iframe.contentWindow;return t?this._resolveDirectTimelineAdapterFromWindow(t):null}catch{return null}}resolveDirectTimelineAdapterFromWindow(t){return this._resolveDirectTimelineAdapterFromWindow(t)}hasRuntimeBridge(t){return Reflect.get(t,"__hf")!==void 0||D(Reflect.get(t,"__player"))}_injectRuntime(){var t,e;this._runtimeInjected=!0;try{const i=this._iframe.contentDocument;if(!i)return;const r=i.createElement("script");r.src=_e,(i.head||i.documentElement).appendChild(r),(e=(t=this._callbacks).onRuntimeInjected)==null||e.call(t)}catch{}}_resolveDirectTimelineAdapterFromWindow(t){var l,p;if(this.hasRuntimeBridge(t))return null;const e=Reflect.get(t,"__timelines");if(!D(e))return null;const i=Object.keys(e);if(i.length===0)return null;const r=(p=(l=this._iframe.contentDocument)==null?void 0:l.querySelector("[data-composition-id]"))==null?void 0:p.getAttribute("data-composition-id"),s=r&&r in e?r:i[i.length-1],a=e[s];return fe(a)?a:null}_resolvePlaybackDurationAdapter(t){const e=Reflect.get(t,"__player");if(me(e))return{kind:"runtime",getDuration:()=>e.getDuration()};const i=this._resolveDirectTimelineAdapterFromWindow(t);return i?{kind:"direct-timeline",timeline:i,getDuration:()=>i.duration()}:null}}const ve=`
2
+ :host {
3
+ display: block;
4
+ position: relative;
5
+ overflow: hidden;
6
+ background: #000;
7
+ contain: layout style;
8
+ }
9
+
10
+ .hfp-container {
11
+ position: absolute;
12
+ inset: 0;
13
+ overflow: hidden;
14
+ pointer-events: none;
15
+ }
16
+
17
+
18
+ .hfp-iframe {
19
+ position: absolute;
20
+ top: 50%;
21
+ left: 50%;
22
+ border: none;
23
+ pointer-events: none;
24
+ }
25
+
26
+ .hfp-poster {
27
+ position: absolute;
28
+ inset: 0;
29
+ object-fit: contain;
30
+ z-index: 1;
31
+ pointer-events: none;
32
+ }
33
+
34
+ .hfp-shader-loader {
35
+ position: absolute;
36
+ inset: 0;
37
+ z-index: 20;
38
+ display: grid;
39
+ place-items: center;
40
+ visibility: hidden;
41
+ opacity: 0;
42
+ pointer-events: none;
43
+ background: #030504;
44
+ color: #f4f7fb;
45
+ cursor: default;
46
+ user-select: none;
47
+ -webkit-user-select: none;
48
+ transition: opacity 420ms ease-out, visibility 420ms ease-out;
49
+ }
50
+
51
+ .hfp-shader-loader.hfp-visible,
52
+ .hfp-shader-loader.hfp-hiding {
53
+ visibility: visible;
54
+ }
55
+
56
+ .hfp-shader-loader.hfp-visible {
57
+ opacity: 1;
58
+ pointer-events: auto;
59
+ }
60
+
61
+ .hfp-shader-loader.hfp-hiding {
62
+ opacity: 0;
63
+ pointer-events: none;
64
+ }
65
+
66
+ .hfp-shader-loader-panel {
67
+ display: grid;
68
+ grid-template-rows: 86px 40px 26px 12px 44px;
69
+ justify-items: center;
70
+ align-items: center;
71
+ gap: 8px;
72
+ width: min(620px, 82%);
73
+ text-align: center;
74
+ font-family: Inter, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
75
+ }
76
+
77
+ .hfp-shader-loader-mark {
78
+ width: 86px;
79
+ height: 86px;
80
+ display: grid;
81
+ place-items: center;
82
+ overflow: visible;
83
+ }
84
+
85
+ .hfp-shader-loader-mark svg {
86
+ display: block;
87
+ overflow: visible;
88
+ filter: drop-shadow(0 0 5px rgba(79, 219, 94, 0.16));
89
+ pointer-events: none;
90
+ }
91
+
92
+ .hfp-shader-loader-title {
93
+ width: 100%;
94
+ height: 40px;
95
+ overflow: hidden;
96
+ white-space: nowrap;
97
+ text-overflow: ellipsis;
98
+ font-size: 26px;
99
+ line-height: 40px;
100
+ font-weight: 700;
101
+ letter-spacing: 0;
102
+ }
103
+
104
+ .hfp-shader-loader-title-text {
105
+ color: transparent;
106
+ background: linear-gradient(
107
+ 90deg,
108
+ rgba(244, 247, 251, 0.84) 0%,
109
+ #ffffff 42%,
110
+ #80efe4 52%,
111
+ #ffffff 62%,
112
+ rgba(244, 247, 251, 0.84) 100%
113
+ );
114
+ background-size: 220% 100%;
115
+ -webkit-background-clip: text;
116
+ background-clip: text;
117
+ animation: hfp-shader-loader-sheen 1.9s linear infinite;
118
+ }
119
+
120
+ .hfp-shader-loader-detail {
121
+ width: 100%;
122
+ height: 26px;
123
+ overflow: hidden;
124
+ white-space: nowrap;
125
+ text-overflow: ellipsis;
126
+ color: rgba(244, 247, 251, 0.62);
127
+ font-size: 15px;
128
+ line-height: 26px;
129
+ font-weight: 500;
130
+ }
131
+
132
+ .hfp-shader-loader-track {
133
+ width: min(360px, 100%);
134
+ height: 8px;
135
+ overflow: hidden;
136
+ border-radius: 999px;
137
+ background: rgba(255, 255, 255, 0.1);
138
+ }
139
+
140
+ .hfp-shader-loader-fill {
141
+ width: 100%;
142
+ height: 100%;
143
+ border-radius: inherit;
144
+ background: linear-gradient(90deg, #06e3fa, #4fdb5e);
145
+ transform: scaleX(0);
146
+ transform-origin: left center;
147
+ transition: transform 160ms ease;
148
+ }
149
+
150
+ .hfp-shader-loader-progress {
151
+ width: min(420px, 100%);
152
+ height: 44px;
153
+ display: grid;
154
+ grid-template-rows: repeat(2, 22px);
155
+ color: rgba(244, 247, 251, 0.48);
156
+ font: 600 13px/22px "IBM Plex Mono", "SF Mono", "Fira Code", "Courier New", monospace;
157
+ font-variant-numeric: tabular-nums;
158
+ }
159
+
160
+ .hfp-shader-loader-row {
161
+ display: grid;
162
+ grid-template-columns: minmax(0, 1fr) 74px;
163
+ align-items: center;
164
+ column-gap: 20px;
165
+ width: 100%;
166
+ white-space: nowrap;
167
+ }
168
+
169
+ .hfp-shader-loader-label {
170
+ min-width: 0;
171
+ overflow: hidden;
172
+ text-align: left;
173
+ text-overflow: ellipsis;
174
+ }
175
+
176
+ .hfp-shader-loader-value {
177
+ text-align: right;
178
+ }
179
+
180
+ @keyframes hfp-shader-loader-sheen {
181
+ from {
182
+ background-position: 140% 0;
183
+ }
184
+ to {
185
+ background-position: -140% 0;
186
+ }
187
+ }
188
+
189
+ /* ── Theming via CSS custom properties ──
190
+ *
191
+ * Override from outside the shadow DOM:
192
+ * hyperframes-player {
193
+ * --hfp-controls-bg: linear-gradient(transparent, rgba(0,0,0,0.9));
194
+ * --hfp-accent: #ff6b6b;
195
+ * --hfp-font: "Inter", sans-serif;
196
+ * }
197
+ */
198
+
199
+ .hfp-controls {
200
+ position: absolute;
201
+ bottom: 0;
202
+ left: 0;
203
+ right: 0;
204
+ display: flex;
205
+ align-items: center;
206
+ gap: var(--hfp-controls-gap, 12px);
207
+ padding: var(--hfp-controls-padding, 8px 16px);
208
+ background: var(--hfp-controls-bg, linear-gradient(transparent, rgba(0, 0, 0, 0.7)));
209
+ color: var(--hfp-color, #fff);
210
+ font-family: var(--hfp-font, system-ui, -apple-system, sans-serif);
211
+ font-size: var(--hfp-font-size, 13px);
212
+ z-index: 10;
213
+ pointer-events: auto;
214
+ opacity: 1;
215
+ transition: opacity 0.3s ease;
216
+ user-select: none;
217
+ }
218
+
219
+ .hfp-controls.hfp-hidden {
220
+ opacity: 0;
221
+ pointer-events: none;
222
+ }
223
+
224
+ .hfp-play-btn {
225
+ background: none;
226
+ border: none;
227
+ color: var(--hfp-color, #fff);
228
+ cursor: pointer;
229
+ padding: 8px;
230
+ display: flex;
231
+ align-items: center;
232
+ justify-content: center;
233
+ width: 40px;
234
+ height: 40px;
235
+ flex-shrink: 0;
236
+ z-index: 10;
237
+ }
238
+
239
+ .hfp-play-btn:hover {
240
+ opacity: 0.8;
241
+ }
242
+
243
+ .hfp-play-btn svg,
244
+ .hfp-play-btn svg * {
245
+ pointer-events: none;
246
+ }
247
+
248
+ .hfp-scrubber {
249
+ flex: 1;
250
+ min-width: 0;
251
+ height: var(--hfp-scrubber-height, 4px);
252
+ background: var(--hfp-scrubber-bg, rgba(255, 255, 255, 0.3));
253
+ border-radius: var(--hfp-scrubber-radius, 2px);
254
+ cursor: pointer;
255
+ position: relative;
256
+ overflow: hidden;
257
+ }
258
+
259
+ .hfp-scrubber:hover {
260
+ height: var(--hfp-scrubber-height-hover, 6px);
261
+ }
262
+
263
+ .hfp-progress {
264
+ position: absolute;
265
+ top: 0;
266
+ left: 0;
267
+ height: 100%;
268
+ background: var(--hfp-accent, #fff);
269
+ pointer-events: none;
270
+ }
271
+
272
+ .hfp-time {
273
+ flex-shrink: 0;
274
+ font-variant-numeric: tabular-nums;
275
+ opacity: 0.9;
276
+ }
277
+
278
+ .hfp-speed-wrap {
279
+ position: relative;
280
+ flex-shrink: 0;
281
+ }
282
+
283
+ .hfp-speed-btn {
284
+ background: var(--hfp-speed-btn-bg, rgba(255, 255, 255, 0.15));
285
+ border: none;
286
+ border-radius: var(--hfp-speed-btn-radius, 4px);
287
+ color: var(--hfp-color, #fff);
288
+ cursor: pointer;
289
+ font-family: var(--hfp-font, system-ui, -apple-system, sans-serif);
290
+ font-size: 12px;
291
+ font-variant-numeric: tabular-nums;
292
+ font-weight: 600;
293
+ padding: 4px 8px;
294
+ min-width: 40px;
295
+ text-align: center;
296
+ transition: background 0.15s ease;
297
+ }
298
+
299
+ .hfp-speed-btn:hover {
300
+ background: var(--hfp-speed-btn-bg-hover, rgba(255, 255, 255, 0.3));
301
+ }
302
+
303
+ .hfp-speed-menu {
304
+ position: absolute;
305
+ bottom: calc(100% + 8px);
306
+ right: 0;
307
+ background: var(--hfp-menu-bg, rgba(20, 20, 20, 0.95));
308
+ backdrop-filter: blur(12px);
309
+ -webkit-backdrop-filter: blur(12px);
310
+ border: 1px solid var(--hfp-menu-border, rgba(255, 255, 255, 0.1));
311
+ border-radius: var(--hfp-menu-radius, 8px);
312
+ padding: 4px;
313
+ display: flex;
314
+ flex-direction: column;
315
+ gap: 2px;
316
+ min-width: 80px;
317
+ opacity: 0;
318
+ visibility: hidden;
319
+ transform: translateY(4px);
320
+ transition: opacity 0.15s ease, transform 0.15s ease, visibility 0.15s;
321
+ box-shadow: var(--hfp-menu-shadow, 0 8px 24px rgba(0, 0, 0, 0.4));
322
+ }
323
+
324
+ .hfp-speed-menu.hfp-open {
325
+ opacity: 1;
326
+ visibility: visible;
327
+ transform: translateY(0);
328
+ }
329
+
330
+ .hfp-speed-option {
331
+ background: none;
332
+ border: none;
333
+ border-radius: 4px;
334
+ color: var(--hfp-menu-color, rgba(255, 255, 255, 0.7));
335
+ cursor: pointer;
336
+ font-family: var(--hfp-font, system-ui, -apple-system, sans-serif);
337
+ font-size: 13px;
338
+ font-variant-numeric: tabular-nums;
339
+ padding: 6px 12px;
340
+ text-align: left;
341
+ transition: background 0.1s ease, color 0.1s ease;
342
+ white-space: nowrap;
343
+ }
344
+
345
+ .hfp-speed-option:hover {
346
+ background: var(--hfp-menu-hover-bg, rgba(255, 255, 255, 0.1));
347
+ color: var(--hfp-color, #fff);
348
+ }
349
+
350
+ .hfp-speed-option.hfp-active {
351
+ color: var(--hfp-accent, #fff);
352
+ font-weight: 600;
353
+ }
354
+
355
+ .hfp-volume-wrap {
356
+ position: relative;
357
+ flex-shrink: 0;
358
+ display: flex;
359
+ align-items: center;
360
+ gap: 0;
361
+ }
362
+
363
+ .hfp-mute-btn {
364
+ background: none;
365
+ border: none;
366
+ color: var(--hfp-color, #fff);
367
+ cursor: pointer;
368
+ padding: 4px;
369
+ display: flex;
370
+ align-items: center;
371
+ justify-content: center;
372
+ width: 32px;
373
+ height: 32px;
374
+ flex-shrink: 0;
375
+ }
376
+
377
+ .hfp-mute-btn:hover {
378
+ opacity: 0.8;
379
+ }
380
+
381
+ .hfp-mute-btn svg,
382
+ .hfp-mute-btn svg * {
383
+ pointer-events: none;
384
+ }
385
+
386
+ .hfp-volume-slider-wrap {
387
+ width: 0;
388
+ overflow: hidden;
389
+ transition: width 0.2s ease;
390
+ display: flex;
391
+ align-items: center;
392
+ }
393
+
394
+ .hfp-volume-wrap:hover .hfp-volume-slider-wrap {
395
+ width: 64px;
396
+ }
397
+
398
+ .hfp-volume-slider {
399
+ width: 56px;
400
+ height: var(--hfp-scrubber-height, 4px);
401
+ background: var(--hfp-scrubber-bg, rgba(255, 255, 255, 0.3));
402
+ border-radius: var(--hfp-scrubber-radius, 2px);
403
+ cursor: pointer;
404
+ position: relative;
405
+ overflow: hidden;
406
+ margin-left: 4px;
407
+ margin-right: 4px;
408
+ }
409
+
410
+ .hfp-volume-fill {
411
+ position: absolute;
412
+ top: 0;
413
+ left: 0;
414
+ height: 100%;
415
+ background: var(--hfp-accent, #fff);
416
+ pointer-events: none;
417
+ }
418
+ `,re='<svg width="24" height="24" viewBox="0 0 18 18" fill="currentColor"><polygon points="4,2 16,9 4,16"/></svg>',ye='<svg width="24" height="24" viewBox="0 0 18 18" fill="currentColor"><rect x="3" y="2" width="4" height="14"/><rect x="11" y="2" width="4" height="14"/></svg>',ne='<svg width="20" height="20" viewBox="0 0 24 24" fill="currentColor"><path d="M3 9v6h4l5 5V4L7 9H3z"/><path d="M16.5 12c0-1.77-1.02-3.29-2.5-4.03v8.05c1.48-.73 2.5-2.25 2.5-4.02z"/><path d="M14 3.23v2.06c2.89.86 5 3.54 5 6.71s-2.11 5.85-5 6.71v2.06c4.01-.91 7-4.49 7-8.77s-2.99-7.86-7-8.77z"/></svg>',se='<svg width="20" height="20" viewBox="0 0 24 24" fill="currentColor"><path d="M3 9v6h4l5 5V4L7 9H3z"/><path d="M16.5 12c0-1.77-1.02-3.29-2.5-4.03v8.05c1.48-.73 2.5-2.25 2.5-4.02z"/></svg>',we='<svg width="20" height="20" viewBox="0 0 24 24" fill="currentColor"><path d="M3 9v6h4l5 5V4L7 9H3z"/><path d="M16.5 12c0-1.77-1.02-3.29-2.5-4.03v8.05c1.48-.73 2.5-2.25 2.5-4.02z" opacity="0.3"/><line x1="18" y1="7" x2="14" y2="17" stroke="currentColor" stroke-width="2"/></svg>',Ae=[.25,.5,1,1.5,2,4];function U(n){return Number.isInteger(n)?`${n}x`:`${n}x`}function oe(n){if(!Number.isFinite(n)||n<0)return"0:00";const t=Math.floor(n),e=Math.floor(t/60),i=t%60;return`${e}:${i.toString().padStart(2,"0")}`}function Ee(n,t,e={}){const i=e.speedPresets??Ae,r=document.createElement("div");r.className="hfp-controls",r.addEventListener("click",o=>{o.stopPropagation()});const s=document.createElement("button");s.className="hfp-play-btn",s.type="button",s.innerHTML=re,s.setAttribute("aria-label","Play");const a=document.createElement("div");a.className="hfp-scrubber";const l=document.createElement("div");l.className="hfp-progress",l.style.width="0%",a.appendChild(l);const p=document.createElement("span");p.className="hfp-time",p.textContent="0:00 / 0:00";const m=document.createElement("div");m.className="hfp-speed-wrap";const u=document.createElement("button");u.className="hfp-speed-btn",u.type="button",u.textContent="1x",u.setAttribute("aria-label","Playback speed");const c=document.createElement("div");c.className="hfp-speed-menu",c.setAttribute("role","menu");for(const o of i){const d=document.createElement("button");d.className="hfp-speed-option",d.type="button",d.setAttribute("role","menuitem"),d.dataset.speed=String(o),d.textContent=U(o),o===1&&d.classList.add("hfp-active"),c.appendChild(d)}m.appendChild(c),m.appendChild(u);const g=document.createElement("div");g.className="hfp-volume-wrap";const f=document.createElement("button");f.className="hfp-mute-btn",f.type="button",f.innerHTML=ne,f.setAttribute("aria-label","Mute");const b=document.createElement("div");b.className="hfp-volume-slider-wrap";const _=document.createElement("div");_.className="hfp-volume-slider",_.setAttribute("role","slider"),_.setAttribute("aria-label","Volume"),_.setAttribute("aria-valuemin","0"),_.setAttribute("aria-valuemax","100"),_.setAttribute("aria-valuenow","100"),_.tabIndex=0;const y=document.createElement("div");y.className="hfp-volume-fill",y.style.width="100%",_.appendChild(y),b.appendChild(_),g.appendChild(b),g.appendChild(f),e.audioLocked&&(g.style.display="none"),r.appendChild(s),r.appendChild(a),r.appendChild(p),r.appendChild(g),r.appendChild(m),n.appendChild(r);let L=!1,A=!1,w=1,k=null;i.indexOf(1);const M=(o,d)=>o?we:d===0||d<.5?se:ne;s.addEventListener("click",o=>{o.stopPropagation(),L?t.onPause():t.onPlay()}),f.addEventListener("click",o=>{o.stopPropagation(),t.onMuteToggle()});let E=!1;const P=o=>{const d=_.getBoundingClientRect(),v=Math.max(0,Math.min(1,(o-d.left)/d.width));w=v,y.style.width=`${v*100}%`,_.setAttribute("aria-valuenow",String(Math.round(v*100))),A&&v>0&&t.onMuteToggle(),f.innerHTML=M(A,v),t.onVolumeChange(v)};_.addEventListener("mousedown",o=>{o.stopPropagation(),E=!0,P(o.clientX)});const j=o=>{E&&P(o.clientX)},B=()=>{E=!1};document.addEventListener("mousemove",j),document.addEventListener("mouseup",B),_.addEventListener("touchstart",o=>{E=!0;const d=o.touches[0];d&&P(d.clientX)},{passive:!0});const W=o=>{if(E){const d=o.touches[0];d&&P(d.clientX)}},q=()=>{E=!1};document.addEventListener("touchmove",W,{passive:!0}),document.addEventListener("touchend",q);const G=.05;_.addEventListener("keydown",o=>{let d=w;if(o.key==="ArrowRight"||o.key==="ArrowUp")d=Math.min(1,w+G);else if(o.key==="ArrowLeft"||o.key==="ArrowDown")d=Math.max(0,w-G);else return;o.preventDefault(),o.stopPropagation(),w=d,y.style.width=`${d*100}%`,_.setAttribute("aria-valuenow",String(Math.round(d*100))),A&&d>0&&t.onMuteToggle(),f.innerHTML=M(A,d),t.onVolumeChange(d)});const X=o=>{for(const d of c.querySelectorAll(".hfp-speed-option"))d.classList.toggle("hfp-active",d.dataset.speed===String(o))};u.addEventListener("click",o=>{o.stopPropagation();const d=c.classList.toggle("hfp-open");u.setAttribute("aria-expanded",String(d))}),c.addEventListener("click",o=>{o.stopPropagation();const d=o.target.closest(".hfp-speed-option");if(!d)return;const v=parseFloat(d.dataset.speed);i.indexOf(v),u.textContent=U(v),X(v),c.classList.remove("hfp-open"),u.setAttribute("aria-expanded","false"),t.onSpeedChange(v)});const Y=()=>{c.classList.remove("hfp-open"),u.setAttribute("aria-expanded","false")};document.addEventListener("click",Y);const R=o=>{const d=a.getBoundingClientRect(),v=Math.max(0,Math.min(1,(o-d.left)/d.width));t.onSeek(v)};let C=!1;a.addEventListener("mousedown",o=>{o.stopPropagation(),C=!0,R(o.clientX)});const Q=o=>{C&&R(o.clientX)},J=()=>{C=!1};document.addEventListener("mousemove",Q),document.addEventListener("mouseup",J),a.addEventListener("touchstart",o=>{C=!0;const d=o.touches[0];d&&R(d.clientX)},{passive:!0});const K=o=>{if(C){const d=o.touches[0];d&&R(d.clientX)}},Z=()=>{C=!1};document.addEventListener("touchmove",K,{passive:!0}),document.addEventListener("touchend",Z);const ee=()=>{k&&clearTimeout(k),k=setTimeout(()=>{L&&r.classList.add("hfp-hidden")},3e3)},I=n instanceof ShadowRoot?n.host:n,te=()=>{r.classList.remove("hfp-hidden"),ee()},ie=()=>{L&&r.classList.add("hfp-hidden")};return I.addEventListener("mousemove",te),I.addEventListener("mouseleave",ie),{updateTime(o,d){const v=d>0?Math.min(o,d):o,he=d>0?v/d*100:0;l.style.width=`${he}%`,p.textContent=`${oe(v)} / ${oe(d)}`},updatePlaying(o){L=o,s.innerHTML=o?ye:re,s.setAttribute("aria-label",o?"Pause":"Play"),o?ee():r.classList.remove("hfp-hidden")},updateSpeed(o){i.indexOf(o),u.textContent=U(o),X(o)},updateMuted(o){A=o,f.innerHTML=M(o,w),f.setAttribute("aria-label",o?"Unmute":"Mute")},updateVolume(o){w=o,y.style.width=`${o*100}%`,_.setAttribute("aria-valuenow",String(Math.round(o*100))),f.innerHTML=M(A,o)},setVolumeControlsHidden(o){g.style.display=o?"none":""},show(){r.style.display=""},hide(){r.style.display="none"},destroy(){document.removeEventListener("mousemove",Q),document.removeEventListener("mouseup",J),document.removeEventListener("touchmove",K),document.removeEventListener("touchend",Z),document.removeEventListener("mousemove",j),document.removeEventListener("mouseup",B),document.removeEventListener("touchmove",W),document.removeEventListener("touchend",q),document.removeEventListener("click",Y),I.removeEventListener("mousemove",te),I.removeEventListener("mouseleave",ie),k&&clearTimeout(k),r.remove()}}}function Ce(n,t,e,i,r,s=!1){const a=i?i.split(",").map(Number).filter(m=>!isNaN(m)&&m>0):void 0,l={...a?{speedPresets:a}:{},audioLocked:s},p=Ee(n,r,l);return p.updateMuted(t),p.updateVolume(e),p}function ae(n,t,e){return t?(e||(e=document.createElement("img"),e.className="hfp-poster",n.appendChild(e)),e.src=t,e):(e==null||e.remove(),null)}function Te(n){return n.composedPath().some(t=>t instanceof HTMLElement&&t.classList.contains("hfp-controls"))}let O=null;function ke(n,t){if(typeof CSSStyleSheet<"u")try{O||(O=new CSSStyleSheet,O.replaceSync(t)),n.adoptedStyleSheets=[O];return}catch{}const e=document.createElement("style");e.textContent=t,n.appendChild(e)}function xe(){const n=document.createElement("div");n.className="hfp-container";const t=document.createElement("iframe");return t.className="hfp-iframe",t.sandbox.add("allow-scripts","allow-same-origin"),t.allow="autoplay; fullscreen",t.referrerPolicy="no-referrer",t.title="HyperFrames Composition",n.appendChild(t),{container:n,iframe:t}}function Se(n,t,e,i){const r=n.offsetWidth,s=n.offsetHeight;if(r===0||s===0)return;const a=Math.min(r/e,s/i);t.style.width=`${e}px`,t.style.height=`${i}px`,t.style.transform=`translate(-50%, -50%) scale(${a})`}const Le=100;class Me{constructor(t){h(this,"_raf",null);h(this,"_lastUpdateMs",0);this._callbacks=t}start(t,e,i,r){this.stop();const s=()=>{if(r()){this._raf=null;return}let a;try{a=t.time()}catch{this._raf=null;return}const l=i();l>0&&(a=Math.min(a,l));const p=l>0&&a>=l,m=performance.now();if((m-this._lastUpdateMs>Le||p)&&(this._lastUpdateMs=m,this._callbacks.onTimeUpdate(a,l)),p){if(this._callbacks.getLoop()){this._callbacks.restart();return}try{t.pause()}catch{}this._callbacks.onPaused(),this._raf=null;return}this._raf=requestAnimationFrame(s)};this._raf=requestAnimationFrame(s)}stop(){this._raf!==null&&(cancelAnimationFrame(this._raf),this._raf=null)}get isRunning(){return this._raf!==null}}function Pe(n){const t=Array.from(n.querySelectorAll("[data-composition-id]"));if(t.length===0)return n.body?[n.body]:[];const e=[];for(const i of t)Ie(i)||e.push(i);return Re(n),e}function Re(n){const t=n.body;if(!t||typeof console>"u"||typeof console.warn!="function")return;const e=t.querySelectorAll("audio[data-start], video[data-start]");if(e.length===0)return;const i=[];for(const r of e)r.closest("[data-composition-id]")||i.push(r);i.length!==0&&console.warn(`[hyperframes-player] selectMediaObserverTargets: composition hosts are present, but ${i.length} body-level timed media element(s) sit outside every [data-composition-id] subtree and will not be observed. Move them inside a composition host or the parent-frame proxy will never adopt them.`,i)}function Ie(n){let t=n.parentElement;for(;t;){if(t.hasAttribute("data-composition-id"))return!0;t=t.parentElement}return!1}const Oe=.05,Ne=2;class De{constructor(t){h(this,"_entries",[]);h(this,"_mediaObserver");h(this,"_playbackErrorPosted",!1);h(this,"_audioOwner","runtime");h(this,"_urlAudioEntry",null);h(this,"_urlAudioSrc",null);h(this,"_dispatchEvent");h(this,"_getMuted");h(this,"_getVolume");h(this,"_getPlaybackRate");h(this,"_getCurrentTime");h(this,"_isPaused");this._dispatchEvent=t.dispatchEvent,this._getMuted=t.getMuted,this._getVolume=t.getVolume,this._getPlaybackRate=t.getPlaybackRate,this._getCurrentTime=t.getCurrentTime,this._isPaused=t.isPaused}get audioOwner(){return this._audioOwner}get entries(){return this._entries}resetForIframeLoad(){this._playbackErrorPosted=!1;const t=this._audioOwner==="parent";this._audioOwner="runtime",this.pauseAll(),this.teardownObserver(),t&&this._dispatchEvent(new CustomEvent("audioownershipchange",{detail:{owner:"runtime",reason:"iframe-reload"}}))}destroy(){this.teardownObserver();for(const t of this._entries)t.el.pause(),t.el.src="";this._entries=[],this._urlAudioEntry=null,this._urlAudioSrc=null}updateMuted(t){for(const e of this._entries)e.el.muted=t}updateVolume(t){for(const e of this._entries)e.el.volume=t}updatePlaybackRate(t){for(const e of this._entries)e.el.playbackRate=t}_playEntry(t){t.el.src&&t.el.play().catch(e=>this._reportPlaybackError(e))}_playEntryIfActive(t){this._refreshEntryBounds(t);const e=this._getCurrentTime()-t.start;e<0||e>=t.duration||this._playEntry(t)}_refreshEntryBounds(t){var r;if(!((r=t.source)!=null&&r.isConnected))return;const e=parseFloat(t.source.getAttribute("data-start")||"0");t.start=Number.isFinite(e)?e:0;const i=parseFloat(t.source.getAttribute("data-duration")||"");t.duration=Number.isFinite(i)&&i>0?i:Number.POSITIVE_INFINITY}_gateEntryPlayback(t,e){return e<0||e>=t.duration?(t.el.paused||t.el.pause(),t.driftSamples=0,!1):(this._audioOwner==="parent"&&!this._isPaused()&&t.el.paused&&this._playEntry(t),!0)}playAll(){for(const t of this._entries)this._playEntryIfActive(t)}pauseAll(){for(const t of this._entries)t.el.pause()}seekAll(t){for(const e of this._entries){this._refreshEntryBounds(e);const i=t-e.start;i>=0&&i<e.duration&&(e.el.currentTime=i)}}mirrorTime(t,e){const i=(e==null?void 0:e.force)===!0;for(const r of this._entries){this._refreshEntryBounds(r);const s=t-r.start;this._gateEntryPlayback(r,s)&&(Math.abs(r.el.currentTime-s)>Oe?(r.driftSamples+=1,(i||r.driftSamples>=Ne)&&(r.el.currentTime=s,r.driftSamples=0)):r.driftSamples=0)}}promoteToParentProxy(t,e){if(this._audioOwner==="parent")return;if(this._audioOwner="parent",t)for(const r of t.querySelectorAll("video, audio"))r.muted=!0;const i=this._getCurrentTime();e?e(i,{force:!0}):this.mirrorTime(i,{force:!0}),this._isPaused()||this.playAll(),this._dispatchEvent(new CustomEvent("audioownershipchange",{detail:{owner:"parent",reason:"autoplay-blocked"}}))}setupFromIframe(t){const e=t.querySelectorAll("audio[data-start], video[data-start]");for(const i of e)this._adoptIframeMedia(i);this._observeDynamicMedia(t)}setupFromUrl(t){if(this._urlAudioSrc===t&&this._urlAudioEntry)return;this.teardownUrlAudio();const e=this._createEntry(t,"audio",0,1/0);this._urlAudioEntry=e,this._urlAudioSrc=e?t:null,e&&this._audioOwner==="parent"&&!this._isPaused()&&(this.mirrorTime(this._getCurrentTime(),{force:!0}),this.playAll())}teardownUrlAudio(){const t=this._urlAudioEntry;if(this._urlAudioEntry=null,this._urlAudioSrc=null,!t)return;t.el.pause(),t.el.src="";const e=this._entries.indexOf(t);e!==-1&&this._entries.splice(e,1)}teardownObserver(){var t;(t=this._mediaObserver)==null||t.disconnect(),this._mediaObserver=void 0}_reportPlaybackError(t){this._playbackErrorPosted||(this._playbackErrorPosted=!0,this._dispatchEvent(new CustomEvent("playbackerror",{detail:{source:"parent-proxy",error:t}})))}_createEntry(t,e,i,r,s){if(this._entries.some(m=>m.el.src===t))return null;const a=e==="video"?document.createElement("video"):new Audio;a.preload="auto",a.src=t,a.load(),a.muted=this._getMuted(),a.volume=this._getVolume();const l=this._getPlaybackRate();l!==1&&(a.playbackRate=l);const p={el:a,start:i,duration:r,driftSamples:0,source:s};return this._entries.push(p),p}_resolveIframeMediaSrc(t){var i;const e=t.getAttribute("src")||((i=t.querySelector("source"))==null?void 0:i.getAttribute("src"));return e?new URL(e,t.ownerDocument.baseURI).href:null}_adoptIframeMedia(t){if(t.preload==="metadata"||t.preload==="none")return;const e=this._resolveIframeMediaSrc(t);if(!e)return;const i=parseFloat(t.getAttribute("data-start")||"0"),r=parseFloat(t.getAttribute("data-duration")||"Infinity"),s=t.tagName==="VIDEO"?"video":"audio",a=this._createEntry(e,s,i,r,t);a&&this._audioOwner==="parent"&&(this.mirrorTime(this._getCurrentTime(),{force:!0}),this._isPaused()||this._playEntryIfActive(a))}_detachIframeMedia(t){const e=this._resolveIframeMediaSrc(t);if(!e)return;const i=this._entries.findIndex(s=>s.el.src===e);if(i===-1)return;const r=this._entries[i];r.el.pause(),r.el.src="",this._entries.splice(i,1)}_observeDynamicMedia(t){if(this.teardownObserver(),typeof MutationObserver>"u"||!t.body)return;const e=new MutationObserver(s=>{var a,l,p,m;for(const u of s){if(u.type==="attributes"&&u.attributeName==="preload"){const c=u.target;c instanceof HTMLMediaElement&&c.matches("audio[data-start], video[data-start]")&&c.preload==="auto"&&this._adoptIframeMedia(c);continue}for(const c of u.addedNodes){if(!(c instanceof Element))continue;const g=[];(a=c.matches)!=null&&a.call(c,"audio[data-start], video[data-start]")&&g.push(c);const f=(l=c.querySelectorAll)==null?void 0:l.call(c,"audio[data-start], video[data-start]");if(f)for(const b of f)g.push(b);for(const b of g)this._adoptIframeMedia(b)}for(const c of u.removedNodes){if(!(c instanceof Element))continue;const g=[];(p=c.matches)!=null&&p.call(c,"audio[data-start], video[data-start]")&&g.push(c);const f=(m=c.querySelectorAll)==null?void 0:m.call(c,"audio[data-start], video[data-start]");if(f)for(const b of f)g.push(b);for(const b of g)this._detachIframeMedia(b)}}}),i={childList:!0,subtree:!0,attributes:!0,attributeFilter:["preload"]},r=Pe(t);for(const s of r)e.observe(s,i);this._mediaObserver=e}}const Fe=100;function Ue(n,t,e,i){const r=(n.frame??0)/t,s=e.duration>0?Math.min(r,e.duration):r,a=!e.paused,l=!n.isPlaying,p=e.duration>0&&s>=e.duration&&(a||n.isPlaying);if(p&&i.getLoop())return i.media.audioOwner==="parent"&&i.media.pauseAll(),i.seek(0),i.play(),{...e,currentTime:s,paused:!1};const m={...e,currentTime:s,paused:l};i.media.audioOwner==="parent"&&(a&&l?i.media.pauseAll():!a&&!l&&i.media.playAll(),i.media.mirrorTime(s));const u=performance.now(),c=l!==e.paused;return(u-e.lastUpdateMs>Fe||c)&&(m.lastUpdateMs=u,i.updateControlsTime(s,e.duration),i.updateControlsPlaying(!l),i.dispatchEvent(new CustomEvent("timeupdate",{detail:{currentTime:s}}))),p&&(i.media.audioOwner==="parent"&&i.media.pauseAll(),m.paused=!0,i.updateControlsPlaying(!1),i.dispatchEvent(new Event("ended"))),m}const de=30;function He(n,t,e){if(n.source!==t)return;const i=n.data;if(!(!i||i.source!=="hf-preview")){if(i.type==="shader-transition-state"){const r=i.state&&typeof i.state=="object"?i.state:{};e.shaderLoader.update(r,e.getShaderLoadingMode()),e.dispatchEvent(new CustomEvent("shadertransitionstate",{detail:{compositionId:i.compositionId,state:r}}));return}if(i.type==="ready"){e.onRuntimeReady();return}if(i.type==="state"){e.setPlaybackState(Ue({frame:i.frame??0,isPlaying:!!i.isPlaying},de,e.getPlaybackState(),e));return}if(i.type==="media-autoplay-blocked"){let r=null;try{r=e.getIframeDoc()}catch{}e.media.promoteToParentProxy(r,(s,a)=>e.media.mirrorTime(s,a)),e.sendControl("set-media-output-muted",{muted:!0});return}if(i.type==="timeline"&&i.durationInFrames>0){if(Number.isFinite(i.durationInFrames)){const r=e.getPlaybackState(),s=i.durationInFrames/de;e.setPlaybackState({...r,duration:s}),e.updateControlsTime(r.currentTime,s)}return}i.type==="stage-size"&&Number.isFinite(i.width)&&i.width>0&&Number.isFinite(i.height)&&i.height>0&&e.setCompositionSize(i.width,i.height)}}const T="shader-capture-scale",x="shader-loading",Ve="__hf_shader_capture_scale",$e="__hf_shader_loading",N=["Preparing scene transitions","Sampling outgoing scene motion","Sampling incoming scene motion","Caching transition frames","Finalizing transition preview"];function z(n){if(n===null)return null;const t=Number(n);return!Number.isFinite(t)||t<=0?null:String(Math.min(1,Math.max(.25,t)))}function ze(n){if(n===null||n.trim()==="")return"composition";const t=n.trim().toLowerCase();return t==="none"||t==="false"||t==="0"||t==="off"?"none":t==="player"||t==="true"||t==="1"||t==="on"?"player":"composition"}function le(n,t,e){e===null?n.delete(t):n.set(t,e)}function je(n,t,e){const i=n.indexOf("#"),r=i>=0?n.slice(0,i):n,s=i>=0?n.slice(i):"",a=r.indexOf("?"),l=a>=0?r.slice(0,a):r,p=a>=0?r.slice(a+1):"",m=new URLSearchParams(p);le(m,Ve,t),le(m,$e,e==="composition"?null:e);const u=m.toString();return`${l}${u?`?${u}`:""}${s}`}function Be(n,t,e){if(t===null&&e==="composition")return n;const i=[];t!==null&&i.push(`window.__HF_SHADER_CAPTURE_SCALE=${JSON.stringify(t)};`),e!=="composition"&&i.push(`window.__HF_SHADER_LOADING=${JSON.stringify(e)};`);const r=`<script data-hyperframes-player-shader-options>${i.join("")}<\/script>`;return/<head\b[^>]*>/i.test(n)?n.replace(/<head\b[^>]*>/i,s=>`${s}${r}`):/<html\b[^>]*>/i.test(n)?n.replace(/<html\b[^>]*>/i,s=>`${s}${r}`):`${r}${n}`}function S(n){return ze(n.getAttribute(x))}function We(n){return Number(z(n.getAttribute(T))??"1")}function H(n,t){return je(t,z(n.getAttribute(T)),S(n))}function V(n,t){return Be(t,z(n.getAttribute(T)),S(n))}function qe(){const n=document.createElement("div");n.className="hfp-shader-loader",n.setAttribute("role","status"),n.setAttribute("aria-live","polite"),n.setAttribute("aria-label","Preparing scene transitions"),n.setAttribute("data-hyperframes-ignore",""),n.draggable=!1;const t=f=>{f.preventDefault(),f.stopPropagation()};for(const f of["selectstart","dragstart","pointerdown","mousedown","click","dblclick","contextmenu","touchstart"])n.addEventListener(f,t,{capture:!0});const e=document.createElement("div");e.className="hfp-shader-loader-panel",e.draggable=!1;const i=document.createElement("div");i.className="hfp-shader-loader-mark",i.draggable=!1,i.innerHTML=['<svg width="78" height="78" viewBox="0 0 100 100" fill="none" aria-hidden="true" draggable="false">','<path d="M10.1851 57.8021L33.1145 73.8313C36.2202 75.9978 41.5173 73.5433 42.4816 69.4984L51.7611 30.4271C52.7253 26.3822 48.5802 23.9277 44.4602 26.0942L13.917 42.1235C6.96677 45.7676 4.97564 54.1579 10.1851 57.8021Z" fill="url(#hfp-shader-loader-grad-left)"/>','<path d="M87.5129 57.5141L56.9696 73.5433C52.8371 75.7098 48.7046 73.2553 49.6688 69.2104L58.9483 30.1391C59.9125 26.0942 65.2097 23.6397 68.3154 25.8062L91.2447 41.8354C96.4668 45.4796 94.4631 53.8699 87.5129 57.5141Z" fill="url(#hfp-shader-loader-grad-right)"/>',"<defs>",'<linearGradient id="hfp-shader-loader-grad-left" x1="48.5676" y1="25" x2="44.7804" y2="71.9384" gradientUnits="userSpaceOnUse">','<stop stop-color="#06E3FA"/>','<stop offset="1" stop-color="#4FDB5E"/>',"</linearGradient>",'<linearGradient id="hfp-shader-loader-grad-right" x1="54.8282" y1="73.8392" x2="72.0989" y2="32.8932" gradientUnits="userSpaceOnUse">','<stop stop-color="#06E3FA"/>','<stop offset="1" stop-color="#4FDB5E"/>',"</linearGradient>","</defs>","</svg>"].join("");const r=document.createElement("div");r.className="hfp-shader-loader-title";const s=document.createElement("span");s.className="hfp-shader-loader-title-text",s.textContent=N[0],r.appendChild(s);const a=document.createElement("div");a.className="hfp-shader-loader-detail",a.textContent="Rendering animated scene samples for shader transitions.";const l=document.createElement("div");l.className="hfp-shader-loader-track",l.setAttribute("aria-hidden","true");const p=document.createElement("div");p.className="hfp-shader-loader-fill",l.appendChild(p);const m=document.createElement("div");m.className="hfp-shader-loader-progress";const u=f=>{const b=document.createElement("div");b.className="hfp-shader-loader-row";const _=document.createElement("span");_.className="hfp-shader-loader-label",_.textContent=f;const y=document.createElement("span");return y.className="hfp-shader-loader-value",b.appendChild(_),b.appendChild(y),m.appendChild(b),{row:b,label:_,value:y}},c=u("transition"),g=u("transition frame");return e.appendChild(i),e.appendChild(r),e.appendChild(a),e.appendChild(l),e.appendChild(m),n.appendChild(e),{root:n,fill:p,title:s,detail:a,transitionValue:c.value,frameLabel:g.label,frameValue:g.value,frameRow:g.row}}const Ge=420;class Xe{constructor(t){h(this,"_el");h(this,"_hideTimeout",null);this._el=t}show(){this._hideTimeout&&(clearTimeout(this._hideTimeout),this._hideTimeout=null),this._el.root.classList.remove("hfp-hiding"),this._el.root.classList.add("hfp-visible")}hide(){if(this._el.root.classList.contains("hfp-hiding")){this._hideTimeout||this._scheduleCleanup();return}this._el.root.classList.contains("hfp-visible")&&(this._el.root.classList.add("hfp-hiding"),this._el.root.classList.remove("hfp-visible"),this._scheduleCleanup())}reset(){this._hideTimeout&&(clearTimeout(this._hideTimeout),this._hideTimeout=null),this._el.root.classList.remove("hfp-visible","hfp-hiding"),this._el.fill.style.transform="scaleX(0)",this._el.transitionValue.textContent="",this._el.frameValue.textContent="",this._el.frameRow.style.visibility="hidden"}update(t,e){if(e!=="player"){this.reset();return}if(t.ready||!t.loading){this.hide();return}const i=typeof t.progress=="number"&&Number.isFinite(t.progress)?t.progress:0,r=typeof t.total=="number"&&Number.isFinite(t.total)?t.total:0,s=r>0?Math.min(1,Math.max(0,i/r)):0,a=Math.min(N.length-1,Math.floor(s*N.length));this._el.title.textContent=N[a]||"Preparing scene transitions",this._el.detail.textContent=t.phase==="cached"?"Loading cached transition frames before playback.":t.phase==="finalizing"?"Uploading transition textures for smooth playback.":"Rendering animated scene samples for shader transitions.",this._el.fill.style.transform=`scaleX(${s})`,this._el.transitionValue.textContent=t.currentTransition!==void 0&&t.transitionTotal!==void 0?`${t.currentTransition}/${t.transitionTotal}`:r>0?`${i}/${r}`:"";const l=t.transitionFrame!==void 0&&t.transitionFrames!==void 0?`${t.transitionFrame}/${t.transitionFrames}`:"";this._el.frameLabel.textContent=t.phase==="cached"?"cached transition frames":t.phase==="finalizing"?"finalizing transition frames":"rendering transition frames",this._el.frameValue.textContent=l,this._el.frameRow.style.visibility=l?"visible":"hidden",this._el.root.setAttribute("aria-valuenow",String(Math.round(s*100))),this.show()}get hideTimeout(){return this._hideTimeout}destroy(){this._hideTimeout&&(clearTimeout(this._hideTimeout),this._hideTimeout=null)}_scheduleCleanup(){this._hideTimeout&&clearTimeout(this._hideTimeout),this._hideTimeout=setTimeout(()=>{this._el.root.classList.remove("hfp-hiding"),this._hideTimeout=null},Ge)}}const Ye=.1,Qe=5;function $(n){return!Number.isFinite(n)||n<=0?1:Math.max(Ye,Math.min(Qe,n))}class Je extends HTMLElement{constructor(){super();h(this,"shadow");h(this,"container");h(this,"iframe");h(this,"posterEl",null);h(this,"controlsApi",null);h(this,"resizeObserver");h(this,"shaderLoader");h(this,"probe");h(this,"_ready",!1);h(this,"_currentTime",0);h(this,"_duration",0);h(this,"_paused",!0);h(this,"_lastUpdateMs",0);h(this,"_volume",1);h(this,"_compositionWidth",1920);h(this,"_compositionHeight",1080);h(this,"_directTimelineAdapter",null);h(this,"_directTimelineClock");h(this,"_parentTickRaf",null);h(this,"_media");this.shadow=this.attachShadow({mode:"open"}),ke(this.shadow,ve),{container:this.container,iframe:this.iframe}=xe(),this.shadow.appendChild(this.container);const e=qe();this.shadow.appendChild(e.root),this.shaderLoader=new Xe(e),this._media=new De({dispatchEvent:i=>this.dispatchEvent(i),getMuted:()=>this.muted,getVolume:()=>this._volume,getPlaybackRate:()=>this.playbackRate,getCurrentTime:()=>this._currentTime,isPaused:()=>this._paused}),this._directTimelineClock=new Me({onTimeUpdate:(i,r)=>{var s;this._currentTime=i,(s=this.controlsApi)==null||s.updateTime(i,r),this.dispatchEvent(new CustomEvent("timeupdate",{detail:{currentTime:i}}))},getLoop:()=>this.loop,restart:()=>{this.seek(0),this.play()},onPaused:()=>{var i;this._media.audioOwner==="parent"&&this._media.pauseAll(),this._paused=!0,(i=this.controlsApi)==null||i.updatePlaying(!1),this.dispatchEvent(new Event("ended"))},onEnded:()=>this.loop}),this.probe=new be(this.iframe,{onReady:i=>this._onProbeReady(i),onError:i=>this.dispatchEvent(new CustomEvent("error",{detail:{message:i}}))}),this.addEventListener("click",i=>{Te(i)||(this._paused?this.play():this.pause())}),this.resizeObserver=new ResizeObserver(()=>this._rescale()),this._onMessage=this._onMessage.bind(this),this._onIframeLoad=this._onIframeLoad.bind(this)}static get observedAttributes(){return["src","srcdoc","width","height","controls","muted","audio-locked","volume","poster","playback-rate","audio-src",T,x]}connectedCallback(){this.resizeObserver.observe(this),window.addEventListener("message",this._onMessage),this.iframe.addEventListener("load",this._onIframeLoad),this.hasAttribute("controls")&&this._setupControls(),this.hasAttribute("poster")&&(this.posterEl=ae(this.shadow,this.getAttribute("poster"),this.posterEl)),this.hasAttribute("audio-src")&&this._media.setupFromUrl(this.getAttribute("audio-src")),this.hasAttribute("srcdoc")&&(this.iframe.srcdoc=V(this,this.getAttribute("srcdoc"))),this.hasAttribute("src")&&(this.iframe.src=H(this,this.getAttribute("src"))),!this.hasAttribute("audio-locked")&&this._isLockedHostEnvironment()&&this._applyAudioLock(!0)}disconnectedCallback(){var e;this.resizeObserver.disconnect(),window.removeEventListener("message",this._onMessage),this.iframe.removeEventListener("load",this._onIframeLoad),this.probe.stop(),this._directTimelineClock.stop(),this._stopParentTickClock(),this._directTimelineAdapter=null,this.shaderLoader.destroy(),this._media.destroy(),(e=this.controlsApi)==null||e.destroy()}attributeChangedCallback(e,i,r){var s,a,l,p,m;switch(e){case"src":r&&(this._ready=!1,this.iframe.src=H(this,r));break;case"srcdoc":this._ready=!1,r!==null?this.iframe.srcdoc=V(this,r):this.iframe.removeAttribute("srcdoc");break;case"width":this._compositionWidth=F(r)??1920,this._rescale();break;case"height":this._compositionHeight=F(r)??1080,this._rescale();break;case"controls":r!==null?this._setupControls():((s=this.controlsApi)==null||s.destroy(),this.controlsApi=null);break;case"poster":this.posterEl=ae(this.shadow,r,this.posterEl);break;case"playback-rate":{const u=$(parseFloat(r||"1"));this._media.updatePlaybackRate(u),this._sendControl("set-playback-rate",{playbackRate:u}),(l=(a=this._directTimelineAdapter)==null?void 0:a.timeScale)==null||l.call(a,u),(p=this.controlsApi)==null||p.updateSpeed(u),this.dispatchEvent(new Event("ratechange"));break}case"muted":this._handleMutedChange(r);break;case"audio-locked":this._applyAudioLock(r!==null);break;case"volume":{const u=Math.max(0,Math.min(1,parseFloat(r||"1")));this._volume=u,this._media.updateVolume(u),this._sendControl("set-volume",{volume:u}),(m=this.controlsApi)==null||m.updateVolume(u),this.dispatchEvent(new Event("volumechange"));break}case"audio-src":r?this._media.setupFromUrl(r):this._media.teardownUrlAudio();break;case T:case x:this._reloadShaderOptions();break}}get iframeElement(){return this.iframe}play(){var i,r;(i=this.posterEl)==null||i.remove(),this.posterEl=null,this._duration>0&&this._currentTime>=this._duration&&this.seek(0),this._paused=!1;const e=this._tryDirectTimelinePlay();e||(this._sendControl("play"),this._ready&&!this._directTimelineAdapter&&this._startParentTickClock()),this._media.audioOwner==="parent"&&this._media.playAll(),(r=this.controlsApi)==null||r.updatePlaying(!0),this.dispatchEvent(new Event("play")),e&&this._directTimelineAdapter&&this._directTimelineClock.start(this._directTimelineAdapter,()=>this._currentTime,()=>this._duration,()=>this._paused)}pause(){var e;this._tryDirectTimelinePause()||this._sendControl("pause"),this._directTimelineClock.stop(),this._stopParentTickClock(),this._media.audioOwner==="parent"&&this._media.pauseAll(),this._paused=!0,(e=this.controlsApi)==null||e.updatePlaying(!1),this.dispatchEvent(new Event("pause"))}seek(e){var i,r;!this._trySyncSeek(e)&&!this._tryDirectTimelineSeek(e)&&this._sendControl("seek",{frame:Math.round(e*30)}),this._directTimelineClock.stop(),this._stopParentTickClock(),this._currentTime=e,this._media.audioOwner==="parent"&&(this._media.pauseAll(),this._media.seekAll(e)),this._paused=!0,(i=this.controlsApi)==null||i.updatePlaying(!1),(r=this.controlsApi)==null||r.updateTime(this._currentTime,this._duration)}setColorGrading(e,i){this._sendControl("set-color-grading",{target:e,grading:i})}clearColorGrading(e){this._sendControl("set-color-grading",{target:e,grading:null})}setColorGradingCompare(e,i){this._sendControl("set-color-grading-compare",{target:e,compare:i})}clearColorGradingCompare(e){this._sendControl("set-color-grading-compare",{target:e,compare:{enabled:!1}})}get currentTime(){return this._currentTime}set currentTime(e){this.seek(e)}get duration(){return this._duration}get paused(){return this._paused}get ready(){return this._ready}get playbackRate(){return $(parseFloat(this.getAttribute("playback-rate")||"1"))}set playbackRate(e){this.setAttribute("playback-rate",String($(e)))}get shaderCaptureScale(){return We(this)}set shaderCaptureScale(e){this.setAttribute(T,String(e))}get shaderLoading(){return S(this)}set shaderLoading(e){e==="composition"?this.removeAttribute(x):this.setAttribute(x,e)}get muted(){return this.hasAttribute("muted")}set muted(e){e?this.setAttribute("muted",""):this.removeAttribute("muted")}get audioLocked(){return this.hasAttribute("audio-locked")}set audioLocked(e){e?this.setAttribute("audio-locked",""):this.removeAttribute("audio-locked")}_isLockedHostEnvironment(){if(typeof navigator>"u")return!1;const e=navigator.userAgent||"";return/\bClaude\/\d/.test(e)&&/\bElectron\b/.test(e)}_isAudioLocked(){return this.hasAttribute("audio-locked")||this._isLockedHostEnvironment()}_handleMutedChange(e){var i;if(e===null&&this._isAudioLocked()){this.setAttribute("muted","");return}this._media.updateMuted(e!==null),this._sendControl("set-muted",{muted:e!==null}),(i=this.controlsApi)==null||i.updateMuted(e!==null),this.dispatchEvent(new Event("volumechange"))}_applyAudioLock(e){var i;e&&(this.muted=!0),(i=this.controlsApi)==null||i.setVolumeControlsHidden(e)}get volume(){return this._volume}set volume(e){this.setAttribute("volume",String(Math.max(0,Math.min(1,e))))}get loop(){return this.hasAttribute("loop")}set loop(e){e?this.setAttribute("loop",""):this.removeAttribute("loop")}_sendControl(e,i={}){var r;try{(r=this.iframe.contentWindow)==null||r.postMessage({source:"hf-parent",type:"control",action:e,...i},"*")}catch{}}_replayBridgeState(){this._sendControl("set-muted",{muted:this.muted}),this._sendControl("set-volume",{volume:this._volume}),this._sendControl("set-playback-rate",{playbackRate:this.playbackRate})}_reloadShaderOptions(){if(S(this)!=="player"&&this.shaderLoader.reset(),this.hasAttribute("srcdoc")){this.iframe.srcdoc=V(this,this.getAttribute("srcdoc")||"");return}this.hasAttribute("src")&&(this.iframe.src=H(this,this.getAttribute("src")||""))}_trySyncSeek(e){try{const i=this.iframe.contentWindow,r=i==null?void 0:i.__player;return typeof(r==null?void 0:r.seek)!="function"?!1:(r.seek.call(r,e),!0)}catch{return!1}}_withDirectTimeline(e){const i=this._directTimelineAdapter||this.probe.resolveDirectTimelineAdapter();if(!i)return!1;try{return e(i),this._directTimelineAdapter=i,!0}catch{return!1}}_tryDirectTimelineSeek(e){return this._withDirectTimeline(i=>{i.seek(e),i.pause()})}_tryDirectTimelinePlay(){return this._withDirectTimeline(e=>void e.play())}_tryDirectTimelinePause(){return this._withDirectTimeline(e=>void e.pause())}_startParentTickClock(){this._stopParentTickClock();const e=()=>{if(this._paused){this._parentTickRaf=null;return}this._sendControl("tick"),this._parentTickRaf=requestAnimationFrame(e)};this._parentTickRaf=requestAnimationFrame(e)}_stopParentTickClock(){this._parentTickRaf!==null&&(cancelAnimationFrame(this._parentTickRaf),this._parentTickRaf=null)}_onMessage(e){He(e,this.iframe.contentWindow,{getPlaybackState:()=>({currentTime:this._currentTime,duration:this._duration,paused:this._paused,lastUpdateMs:this._lastUpdateMs}),setPlaybackState:({currentTime:i,duration:r,paused:s,lastUpdateMs:a})=>{this._currentTime=i,this._duration=r,this._paused=s,this._lastUpdateMs=a},getShaderLoadingMode:()=>S(this),shaderLoader:this.shaderLoader,setCompositionSize:(i,r)=>{this._compositionWidth=i,this._compositionHeight=r,this._rescale()},sendControl:(i,r)=>this._sendControl(i,r),getIframeDoc:()=>this.iframe.contentDocument,onRuntimeReady:()=>this._replayBridgeState(),updateControlsTime:(i,r)=>{var s;return(s=this.controlsApi)==null?void 0:s.updateTime(i,r)},updateControlsPlaying:i=>{var r;return(r=this.controlsApi)==null?void 0:r.updatePlaying(i)},dispatchEvent:i=>this.dispatchEvent(i),seek:i=>this.seek(i),play:()=>this.play(),getLoop:()=>this.loop,media:this._media})}_onProbeReady({duration:e,adapter:i,compositionSize:r}){var s;this._duration=e,this._directTimelineAdapter=i.kind==="direct-timeline"?i.timeline:null,this._ready=!0,(s=this.controlsApi)==null||s.updateTime(0,e),this.dispatchEvent(new CustomEvent("ready",{detail:{duration:e}})),r&&(this._compositionWidth=r.width,this._compositionHeight=r.height,this._rescale());try{const a=this.iframe.contentDocument;a&&this._media.setupFromIframe(a)}catch{}this.hasAttribute("autoplay")&&this.play()}_rescale(){Se(this,this.iframe,this._compositionWidth,this._compositionHeight)}_onIframeLoad(){this._directTimelineAdapter=null,this._directTimelineClock.stop(),this._stopParentTickClock(),this.shaderLoader.reset(),this._media.resetForIframeLoad(),this.probe.start()}_setupControls(){this.controlsApi||(this.controlsApi=Ce(this.shadow,this.muted,this._volume,this.getAttribute("speed-presets"),{onPlay:()=>this.play(),onPause:()=>this.pause(),onSeek:e=>this.seek(e*this._duration),onSpeedChange:e=>void(this.playbackRate=e),onMuteToggle:()=>void(this.muted=!this.muted),onVolumeChange:e=>void(this.volume=e)},this._isAudioLocked()))}get _audioOwner(){return this._media.audioOwner}get _parentMedia(){return this._media.entries}_mirrorParentMediaTime(e,i){this._media.mirrorTime(e,i)}_promoteToParentProxy(){let e=null;try{e=this.iframe.contentDocument}catch{}this._media.promoteToParentProxy(e,(i,r)=>this._mirrorParentMediaTime(i,r)),this._sendControl("set-media-output-muted",{muted:!0})}_observeDynamicMedia(e){this._media.setupFromIframe(e)}}customElements.get("hyperframes-player")||customElements.define("hyperframes-player",Je);export{Je as HyperframesPlayer,Ae as SPEED_PRESETS,U as formatSpeed,oe as formatTime};