@hyperframes/player 0.5.0-alpha.9 → 0.5.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.
package/README.md CHANGED
@@ -52,18 +52,35 @@ Show a static image before playback starts:
52
52
 
53
53
  ## Attributes
54
54
 
55
- | Attribute | Type | Default | Description |
56
- | --------------- | ------- | ------- | -------------------------------------------- |
57
- | `src` | string | — | URL to the composition HTML file |
58
- | `audio-src` | string | — | Audio URL for parent-frame playback (mobile) |
59
- | `width` | number | 1920 | Composition width in pixels (aspect ratio) |
60
- | `height` | number | 1080 | Composition height in pixels (aspect ratio) |
61
- | `controls` | boolean | false | Show play/pause, scrubber, and time display |
62
- | `muted` | boolean | false | Mute audio playback |
63
- | `poster` | string | — | Image URL shown before playback starts |
64
- | `playback-rate` | number | 1 | Speed multiplier (0.5 = half, 2 = double) |
65
- | `autoplay` | boolean | false | Start playing when ready |
66
- | `loop` | boolean | false | Restart when the composition ends |
55
+ | Attribute | Type | Default | Description |
56
+ | ---------------------- | ------------------------------- | ------------- | --------------------------------------------------------------------------- |
57
+ | `src` | string | — | URL to the composition HTML file |
58
+ | `audio-src` | string | — | Audio URL for parent-frame playback (mobile) |
59
+ | `width` | number | 1920 | Composition width in pixels (aspect ratio) |
60
+ | `height` | number | 1080 | Composition height in pixels (aspect ratio) |
61
+ | `controls` | boolean | false | Show play/pause, scrubber, and time display |
62
+ | `muted` | boolean | false | Mute audio playback |
63
+ | `poster` | string | — | Image URL shown before playback starts |
64
+ | `playback-rate` | number | 1 | Speed multiplier (0.5 = half, 2 = double) |
65
+ | `autoplay` | boolean | false | Start playing when ready |
66
+ | `loop` | boolean | false | Restart when the composition ends |
67
+ | `shader-capture-scale` | number | — | Shader transition snapshot scale forwarded to browser previews (`0.25`-`1`) |
68
+ | `shader-loading` | `composition \| player \| none` | `composition` | Controls shader transition prep loading UI ownership |
69
+
70
+ ### Shader transition previews
71
+
72
+ When a composition uses `@hyperframes/shader-transitions`, the player can own preview-only shader capture settings:
73
+
74
+ ```html
75
+ <hyperframes-player
76
+ src="./composition/index.html"
77
+ shader-capture-scale="1"
78
+ shader-loading="player"
79
+ controls
80
+ ></hyperframes-player>
81
+ ```
82
+
83
+ `shader-loading="player"` shows the player-owned transition-prep overlay from shader progress messages. `composition` leaves direct composition fallback behavior alone, and `none` suppresses the loader.
67
84
 
68
85
  ### Mobile audio
69
86
 
@@ -98,6 +115,8 @@ player.ready; // boolean (read-only)
98
115
  player.playbackRate; // number (read/write)
99
116
  player.muted; // boolean (read/write)
100
117
  player.loop; // boolean (read/write)
118
+ player.shaderCaptureScale; // number (read/write)
119
+ player.shaderLoading; // "composition" | "player" | "none" (read/write)
101
120
 
102
121
  // Inner iframe access (for advanced consumers — see "Advanced: iframe access" below)
103
122
  player.iframeElement; // HTMLIFrameElement (read-only)
@@ -157,14 +176,15 @@ function StudioPreview({ src }: { src: string }) {
157
176
 
158
177
  ## Events
159
178
 
160
- | Event | Detail | Fired when |
161
- | ------------ | ----------------- | ------------------------------------------ |
162
- | `ready` | `{ duration }` | Composition loaded and duration determined |
163
- | `play` | — | Playback started |
164
- | `pause` | — | Playback paused |
165
- | `timeupdate` | `{ currentTime }` | Playback position changed (~10 fps) |
166
- | `ended` | — | Reached the end (when not looping) |
167
- | `error` | `{ message }` | Composition failed to load |
179
+ | Event | Detail | Fired when |
180
+ | ----------------------- | -------------------------- | ------------------------------------------ |
181
+ | `ready` | `{ duration }` | Composition loaded and duration determined |
182
+ | `play` | — | Playback started |
183
+ | `pause` | — | Playback paused |
184
+ | `timeupdate` | `{ currentTime }` | Playback position changed (~10 fps) |
185
+ | `ended` | — | Reached the end (when not looping) |
186
+ | `error` | `{ message }` | Composition failed to load |
187
+ | `shadertransitionstate` | `{ compositionId, state }` | Shader transition cache/capture progress |
168
188
 
169
189
  ```js
170
190
  player.addEventListener("ready", (e) => {
@@ -1,4 +1,4 @@
1
- "use strict";var w=Object.defineProperty;var j=Object.getOwnPropertyDescriptor;var z=Object.getOwnPropertyNames;var W=Object.prototype.hasOwnProperty;var q=(o,e)=>{for(var t in e)w(o,t,{get:e[t],enumerable:!0})},$=(o,e,t,r)=>{if(e&&typeof e=="object"||typeof e=="function")for(let i of z(e))!W.call(o,i)&&i!==t&&w(o,i,{get:()=>e[i],enumerable:!(r=j(e,i))||r.enumerable});return o};var Y=o=>$(w({},"__esModule",{value:!0}),o);var V={};q(V,{HyperframesPlayer:()=>E,SPEED_PRESETS:()=>x,formatSpeed:()=>_,formatTime:()=>S});module.exports=Y(V);var M=`
1
+ "use strict";var C=Object.defineProperty;var B=Object.getOwnPropertyDescriptor;var G=Object.getOwnPropertyNames;var Y=Object.prototype.hasOwnProperty;var X=(a,e)=>{for(var t in e)C(a,t,{get:e[t],enumerable:!0})},Q=(a,e,t,r)=>{if(e&&typeof e=="object"||typeof e=="function")for(let i of G(e))!Y.call(a,i)&&i!==t&&C(a,i,{get:()=>e[i],enumerable:!(r=B(e,i))||r.enumerable});return a};var J=a=>Q(C({},"__esModule",{value:!0}),a);var ae={};X(ae,{HyperframesPlayer:()=>T,SPEED_PRESETS:()=>P,formatSpeed:()=>L,formatTime:()=>x});module.exports=J(ae);var A=`
2
2
  :host {
3
3
  display: block;
4
4
  position: relative;
@@ -31,6 +31,161 @@
31
31
  pointer-events: none;
32
32
  }
33
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
+
34
189
  /* \u2500\u2500 Theming via CSS custom properties \u2500\u2500
35
190
  *
36
191
  * Override from outside the shadow DOM:
@@ -195,5 +350,5 @@
195
350
  color: var(--hfp-accent, #fff);
196
351
  font-weight: 600;
197
352
  }
198
- `,C='<svg width="24" height="24" viewBox="0 0 18 18" fill="currentColor"><polygon points="4,2 16,9 4,16"/></svg>',N='<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>';var x=[.25,.5,1,1.5,2,4];function _(o){return Number.isInteger(o)?`${o}x`:`${o}x`}function S(o){if(!Number.isFinite(o)||o<0)return"0:00";let e=Math.floor(o),t=Math.floor(e/60),r=e%60;return`${t}:${r.toString().padStart(2,"0")}`}function F(o,e,t={}){let r=t.speedPresets??x,i=document.createElement("div");i.className="hfp-controls",i.addEventListener("click",s=>{s.stopPropagation()});let d=document.createElement("button");d.className="hfp-play-btn",d.type="button",d.innerHTML=C,d.setAttribute("aria-label","Play");let n=document.createElement("div");n.className="hfp-scrubber";let p=document.createElement("div");p.className="hfp-progress",p.style.width="0%",n.appendChild(p);let h=document.createElement("span");h.className="hfp-time",h.textContent="0:00 / 0:00";let c=document.createElement("div");c.className="hfp-speed-wrap";let l=document.createElement("button");l.className="hfp-speed-btn",l.type="button",l.textContent="1x",l.setAttribute("aria-label","Playback speed");let u=document.createElement("div");u.className="hfp-speed-menu",u.setAttribute("role","menu");for(let s of r){let a=document.createElement("button");a.className="hfp-speed-option",a.type="button",a.setAttribute("role","menuitem"),a.dataset.speed=String(s),a.textContent=_(s),s===1&&a.classList.add("hfp-active"),u.appendChild(a)}c.appendChild(u),c.appendChild(l),i.appendChild(d),i.appendChild(n),i.appendChild(h),i.appendChild(c),o.appendChild(i);let m=!1,v=null,y=r.indexOf(1);y===-1&&(y=0),d.addEventListener("click",s=>{s.stopPropagation(),m?e.onPause():e.onPlay()});let P=s=>{for(let a of u.querySelectorAll(".hfp-speed-option"))a.classList.toggle("hfp-active",a.dataset.speed===String(s))};l.addEventListener("click",s=>{s.stopPropagation();let a=u.classList.toggle("hfp-open");l.setAttribute("aria-expanded",String(a))}),u.addEventListener("click",s=>{s.stopPropagation();let a=s.target.closest(".hfp-speed-option");if(!a)return;let f=parseFloat(a.dataset.speed);y=r.indexOf(f),l.textContent=_(f),P(f),u.classList.remove("hfp-open"),l.setAttribute("aria-expanded","false"),e.onSpeedChange(f)});let A=()=>{u.classList.remove("hfp-open"),l.setAttribute("aria-expanded","false")};document.addEventListener("click",A);let g=s=>{let a=n.getBoundingClientRect(),f=Math.max(0,Math.min(1,(s-a.left)/a.width));e.onSeek(f)},b=!1;n.addEventListener("mousedown",s=>{s.stopPropagation(),b=!0,g(s.clientX)});let L=s=>{b&&g(s.clientX)},I=()=>{b=!1};document.addEventListener("mousemove",L),document.addEventListener("mouseup",I),n.addEventListener("touchstart",s=>{b=!0;let a=s.touches[0];a&&g(a.clientX)},{passive:!0});let R=s=>{if(b){let a=s.touches[0];a&&g(a.clientX)}},O=()=>{b=!1};document.addEventListener("touchmove",R,{passive:!0}),document.addEventListener("touchend",O);let H=()=>{v&&clearTimeout(v),v=setTimeout(()=>{m&&i.classList.add("hfp-hidden")},3e3)},D=o instanceof ShadowRoot?o.host:o;return D.addEventListener("mousemove",()=>{i.classList.remove("hfp-hidden"),H()}),D.addEventListener("mouseleave",()=>{m&&i.classList.add("hfp-hidden")}),{updateTime(s,a){let f=a>0?s/a*100:0;p.style.width=`${f}%`,h.textContent=`${S(s)} / ${S(a)}`},updatePlaying(s){m=s,d.innerHTML=s?N:C,d.setAttribute("aria-label",s?"Pause":"Play"),s?H():i.classList.remove("hfp-hidden")},updateSpeed(s){let a=r.indexOf(s);a!==-1&&(y=a),l.textContent=_(s),P(s)},show(){i.style.display=""},hide(){i.style.display="none"},destroy(){document.removeEventListener("mousemove",L),document.removeEventListener("mouseup",I),document.removeEventListener("touchmove",R),document.removeEventListener("touchend",O),document.removeEventListener("click",A),v&&clearTimeout(v)}}}function U(o){return o.hasRuntime||o.runtimeInjected?!1:!!(o.hasNestedCompositions||o.hasTimelines&&o.attempts>=5)}var k=null;function B(){if(k)return k;if(typeof CSSStyleSheet>"u")return null;try{let o=new CSSStyleSheet;return o.replaceSync(M),k=o,o}catch{return null}}var T=30,X="https://cdn.jsdelivr.net/npm/@hyperframes/core/dist/hyperframe.runtime.iife.js",E=class o extends HTMLElement{static get observedAttributes(){return["src","srcdoc","width","height","controls","muted","poster","playback-rate","audio-src"]}shadow;container;iframe;posterEl=null;controlsApi=null;resizeObserver;_ready=!1;_duration=0;_currentTime=0;_paused=!0;_compositionWidth=1920;_compositionHeight=1080;_probeInterval=null;_lastUpdateMs=0;_parentMedia=[];_audioOwner="runtime";_mediaObserver;_playbackErrorPosted=!1;constructor(){super(),this.shadow=this.attachShadow({mode:"open"});let e=B();if(e)this.shadow.adoptedStyleSheets=[e];else{let t=document.createElement("style");t.textContent=M,this.shadow.appendChild(t)}this.container=document.createElement("div"),this.container.className="hfp-container",this.iframe=document.createElement("iframe"),this.iframe.className="hfp-iframe",this.iframe.sandbox.add("allow-scripts","allow-same-origin"),this.iframe.allow="autoplay; fullscreen",this.iframe.referrerPolicy="no-referrer",this.iframe.title="HyperFrames Composition",this.container.appendChild(this.iframe),this.shadow.appendChild(this.container),this.addEventListener("click",t=>{this._isControlsClick(t)||(this._paused?this.play():this.pause())}),this.resizeObserver=new ResizeObserver(()=>this._updateScale()),this._onMessage=this._onMessage.bind(this),this._onIframeLoad=this._onIframeLoad.bind(this)}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._setupPoster(),this.hasAttribute("audio-src")&&this._setupParentAudioFromUrl(this.getAttribute("audio-src")),this.hasAttribute("srcdoc")&&(this.iframe.srcdoc=this.getAttribute("srcdoc")),this.hasAttribute("src")&&(this.iframe.src=this.getAttribute("src"))}disconnectedCallback(){this.resizeObserver.disconnect(),window.removeEventListener("message",this._onMessage),this.iframe.removeEventListener("load",this._onIframeLoad),this._probeInterval&&clearInterval(this._probeInterval),this._teardownMediaObserver(),this.controlsApi?.destroy();for(let e of this._parentMedia)e.el.pause(),e.el.src="";this._parentMedia=[]}attributeChangedCallback(e,t,r){switch(e){case"src":r&&(this._ready=!1,this.iframe.src=r);break;case"srcdoc":this._ready=!1,r!==null?this.iframe.srcdoc=r:this.iframe.removeAttribute("srcdoc");break;case"width":this._compositionWidth=parseInt(r||"1920",10),this._updateScale();break;case"height":this._compositionHeight=parseInt(r||"1080",10),this._updateScale();break;case"controls":r!==null?this._setupControls():(this.controlsApi?.destroy(),this.controlsApi=null);break;case"poster":this._setupPoster();break;case"playback-rate":{let i=parseFloat(r||"1");for(let d of this._parentMedia)d.el.playbackRate=i;this._sendControl("set-playback-rate",{playbackRate:i}),this.controlsApi?.updateSpeed(i),this.dispatchEvent(new Event("ratechange"));break}case"muted":for(let i of this._parentMedia)i.el.muted=r!==null;this._sendControl("set-muted",{muted:r!==null});break;case"audio-src":r&&this._setupParentAudioFromUrl(r);break}}get iframeElement(){return this.iframe}play(){this._hidePoster(),this._sendControl("play"),this._audioOwner==="parent"&&this._playParentMedia(),this._paused=!1,this.controlsApi?.updatePlaying(!0),this.dispatchEvent(new Event("play"))}pause(){this._sendControl("pause"),this._audioOwner==="parent"&&this._pauseParentMedia(),this._paused=!0,this.controlsApi?.updatePlaying(!1),this.dispatchEvent(new Event("pause"))}seek(e){if(!this._trySyncSeek(e)){let t=Math.round(e*T);this._sendControl("seek",{frame:t})}if(this._currentTime=e,this._audioOwner==="parent")for(let t of this._parentMedia){let r=e-t.start;r>=0&&r<t.duration&&(t.el.currentTime=r)}this._paused=!0,this.controlsApi?.updatePlaying(!1),this.controlsApi?.updateTime(this._currentTime,this._duration)}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 muted(){return this.hasAttribute("muted")}set muted(e){e?this.setAttribute("muted",""):this.removeAttribute("muted")}get loop(){return this.hasAttribute("loop")}set loop(e){e?this.setAttribute("loop",""):this.removeAttribute("loop")}_sendControl(e,t={}){try{this.iframe.contentWindow?.postMessage({source:"hf-parent",type:"control",action:e,...t},"*")}catch{}}_trySyncSeek(e){try{let r=this.iframe.contentWindow?.__player,i=r?.seek;return typeof i!="function"?!1:(i.call(r,e),!0)}catch{return!1}}_isControlsClick(e){return e.composedPath().some(t=>t instanceof HTMLElement&&t.classList.contains("hfp-controls"))}_onMessage(e){if(e.source!==this.iframe.contentWindow)return;let t=e.data;if(!(!t||t.source!=="hf-preview")){if(t.type==="state"){this._currentTime=(t.frame??0)/T;let r=!this._paused;this._paused=!t.isPlaying,this._audioOwner==="parent"&&(r&&this._paused?this._pauseParentMedia():!r&&!this._paused&&this._playParentMedia(),this._mirrorParentMediaTime(this._currentTime));let i=performance.now();(i-this._lastUpdateMs>100||this._paused!==r)&&(this._lastUpdateMs=i,this.controlsApi?.updateTime(this._currentTime,this._duration),this.controlsApi?.updatePlaying(!this._paused),this.dispatchEvent(new CustomEvent("timeupdate",{detail:{currentTime:this._currentTime}}))),this._currentTime>=this._duration&&!this._paused&&(this._audioOwner==="parent"&&this._pauseParentMedia(),this.loop?(this.seek(0),this.play()):(this._paused=!0,this.controlsApi?.updatePlaying(!1),this.dispatchEvent(new Event("ended"))))}t.type==="media-autoplay-blocked"&&this._promoteToParentProxy(),t.type==="timeline"&&t.durationInFrames>0&&Number.isFinite(t.durationInFrames)&&(this._duration=t.durationInFrames/T,this.controlsApi?.updateTime(this._currentTime,this._duration)),t.type==="stage-size"&&t.width>0&&t.height>0&&(this._compositionWidth=t.width,this._compositionHeight=t.height,this._updateScale())}}_runtimeInjected=!1;_onIframeLoad(){let e=0;this._runtimeInjected=!1;let t=this._audioOwner==="parent";this._audioOwner="runtime",this._playbackErrorPosted=!1,this._pauseParentMedia(),this._teardownMediaObserver(),t&&this.dispatchEvent(new CustomEvent("audioownershipchange",{detail:{owner:"runtime",reason:"iframe-reload"}})),this._probeInterval&&clearInterval(this._probeInterval),this._probeInterval=setInterval(()=>{e++;try{let r=this.iframe.contentWindow;if(!r)return;let i=!!(r.__hf||r.__player),d=!!(r.__timelines&&Object.keys(r.__timelines).length>0),n=!!this.iframe.contentDocument?.querySelector("[data-composition-src]");if(U({hasRuntime:i,hasTimelines:d,hasNestedCompositions:n,runtimeInjected:this._runtimeInjected,attempts:e})){this._injectRuntime();return}if(this._runtimeInjected&&!i)return;let h=(()=>{if(r.__player&&typeof r.__player.getDuration=="function")return r.__player;if(r.__timelines){let c=Object.keys(r.__timelines);if(c.length>0){let l=this.iframe.contentDocument?.querySelector("[data-composition-id]")?.getAttribute("data-composition-id"),u=l&&l in r.__timelines?l:c[c.length-1],m=r.__timelines[u];return{getDuration:()=>m.duration()}}}return null})();if(h&&h.getDuration()>0){clearInterval(this._probeInterval),this._duration=h.getDuration(),this._ready=!0,this.controlsApi?.updateTime(0,this._duration),this.dispatchEvent(new CustomEvent("ready",{detail:{duration:this._duration}}));let l=this.iframe.contentDocument?.querySelector("[data-composition-id]");if(l){let u=parseInt(l.getAttribute("data-width")||"0",10),m=parseInt(l.getAttribute("data-height")||"0",10);u>0&&m>0&&(this._compositionWidth=u,this._compositionHeight=m,this._updateScale())}this._setupParentMedia(),this.hasAttribute("autoplay")&&this.play();return}}catch{}e>=40&&(clearInterval(this._probeInterval),this.dispatchEvent(new CustomEvent("error",{detail:{message:"Composition timeline not found after 8s"}})))},200)}_injectRuntime(){this._runtimeInjected=!0;try{let e=this.iframe.contentDocument;if(!e)return;let t=e.createElement("script");t.src=X,t.onload=()=>{},t.onerror=()=>{},(e.head||e.documentElement).appendChild(t)}catch{}}_updateScale(){let e=this.getBoundingClientRect();if(e.width===0||e.height===0)return;let t=Math.min(e.width/this._compositionWidth,e.height/this._compositionHeight);this.iframe.style.width=`${this._compositionWidth}px`,this.iframe.style.height=`${this._compositionHeight}px`,this.iframe.style.transform=`translate(-50%, -50%) scale(${t})`}_setupControls(){if(this.controlsApi)return;let e={onPlay:()=>this.play(),onPause:()=>this.pause(),onSeek:i=>this.seek(i*this._duration),onSpeedChange:i=>{this.playbackRate=i}},t=this.getAttribute("speed-presets"),r=t?t.split(",").map(Number).filter(i=>!isNaN(i)&&i>0):void 0;this.controlsApi=F(this.shadow,e,{speedPresets:r})}_setupPoster(){let e=this.getAttribute("poster");if(!e){this.posterEl?.remove(),this.posterEl=null;return}this.posterEl||(this.posterEl=document.createElement("img"),this.posterEl.className="hfp-poster",this.shadow.appendChild(this.posterEl)),this.posterEl.src=e}_playParentMedia(){for(let e of this._parentMedia)e.el.src&&e.el.play().catch(t=>this._reportPlaybackError(t))}_reportPlaybackError(e){this._playbackErrorPosted||(this._playbackErrorPosted=!0,this.dispatchEvent(new CustomEvent("playbackerror",{detail:{source:"parent-proxy",error:e}})))}_pauseParentMedia(){for(let e of this._parentMedia)e.el.pause()}static MIRROR_DRIFT_THRESHOLD_SECONDS=.05;static MIRROR_REQUIRED_CONSECUTIVE_DRIFT_SAMPLES=2;_mirrorParentMediaTime(e,t){let r=t?.force===!0,i=o.MIRROR_REQUIRED_CONSECUTIVE_DRIFT_SAMPLES,d=o.MIRROR_DRIFT_THRESHOLD_SECONDS;for(let n of this._parentMedia){let p=e-n.start;if(p<0||p>=n.duration){n.driftSamples=0;continue}Math.abs(n.el.currentTime-p)>d?(n.driftSamples+=1,(r||n.driftSamples>=i)&&(n.el.currentTime=p,n.driftSamples=0)):n.driftSamples=0}}_promoteToParentProxy(){this._audioOwner!=="parent"&&(this._audioOwner="parent",this._sendControl("set-media-output-muted",{muted:!0}),this._mirrorParentMediaTime(this._currentTime,{force:!0}),this._paused||this._playParentMedia(),this.dispatchEvent(new CustomEvent("audioownershipchange",{detail:{owner:"parent",reason:"autoplay-blocked"}})))}_createParentMedia(e,t,r,i){if(this._parentMedia.some(p=>p.el.src===e))return null;let d=t==="video"?document.createElement("video"):new Audio;d.preload="auto",d.src=e,d.load(),d.muted=this.muted,this.playbackRate!==1&&(d.playbackRate=this.playbackRate);let n={el:d,start:r,duration:i,driftSamples:0};return this._parentMedia.push(n),n}_setupParentAudioFromUrl(e){this._createParentMedia(e,"audio",0,1/0)}_setupParentMedia(){try{let e=this.iframe.contentDocument;if(!e)return;let t=e.querySelectorAll("audio[data-start], video[data-start]");for(let r of t)this._adoptIframeMedia(r);this._observeDynamicMedia(e)}catch{}}_adoptIframeMedia(e){let t=e.getAttribute("src")||e.querySelector("source")?.getAttribute("src");if(!t)return;let r=new URL(t,e.ownerDocument.baseURI).href,i=parseFloat(e.getAttribute("data-start")||"0"),d=parseFloat(e.getAttribute("data-duration")||"Infinity"),n=e.tagName==="VIDEO"?"video":"audio",p=this._createParentMedia(r,n,i,d);p&&this._audioOwner==="parent"&&(this._mirrorParentMediaTime(this._currentTime,{force:!0}),!this._paused&&p.el.src&&p.el.play().catch(h=>this._reportPlaybackError(h)))}_observeDynamicMedia(e){if(this._teardownMediaObserver(),typeof MutationObserver>"u"||!e.body)return;let t=new MutationObserver(i=>{for(let d of i){for(let n of d.addedNodes){if(!(n instanceof Element))continue;let p=[];n.matches?.("audio[data-start], video[data-start]")&&p.push(n);let h=n.querySelectorAll?.("audio[data-start], video[data-start]");if(h)for(let c of h)p.push(c);for(let c of p)this._adoptIframeMedia(c)}for(let n of d.removedNodes){if(!(n instanceof Element))continue;let p=[];n.matches?.("audio[data-start], video[data-start]")&&p.push(n);let h=n.querySelectorAll?.("audio[data-start], video[data-start]");if(h)for(let c of h)p.push(c);for(let c of p)this._detachIframeMedia(c)}}}),r=e.querySelectorAll("[data-composition-id]");if(r.length>0)for(let i of r)t.observe(i,{childList:!0,subtree:!0});else t.observe(e.body,{childList:!0,subtree:!0});this._mediaObserver=t}_teardownMediaObserver(){this._mediaObserver?.disconnect(),this._mediaObserver=void 0}_detachIframeMedia(e){let t=e.getAttribute("src")||e.querySelector("source")?.getAttribute("src");if(!t)return;let r=new URL(t,e.ownerDocument.baseURI).href,i=this._parentMedia.findIndex(n=>n.el.src===r);if(i===-1)return;let d=this._parentMedia[i];d.el.pause(),d.el.src="",this._parentMedia.splice(i,1)}_hidePoster(){this.posterEl?.remove(),this.posterEl=null}};customElements.get("hyperframes-player")||customElements.define("hyperframes-player",E);0&&(module.exports={HyperframesPlayer,SPEED_PRESETS,formatSpeed,formatTime});
353
+ `,k='<svg width="24" height="24" viewBox="0 0 18 18" fill="currentColor"><polygon points="4,2 16,9 4,16"/></svg>',$='<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>';var P=[.25,.5,1,1.5,2,4];function L(a){return Number.isInteger(a)?`${a}x`:`${a}x`}function x(a){if(!Number.isFinite(a)||a<0)return"0:00";let e=Math.floor(a),t=Math.floor(e/60),r=e%60;return`${t}:${r.toString().padStart(2,"0")}`}function z(a,e,t={}){let r=t.speedPresets??P,i=document.createElement("div");i.className="hfp-controls",i.addEventListener("click",o=>{o.stopPropagation()});let n=document.createElement("button");n.className="hfp-play-btn",n.type="button",n.innerHTML=k,n.setAttribute("aria-label","Play");let s=document.createElement("div");s.className="hfp-scrubber";let d=document.createElement("div");d.className="hfp-progress",d.style.width="0%",s.appendChild(d);let c=document.createElement("span");c.className="hfp-time",c.textContent="0:00 / 0:00";let p=document.createElement("div");p.className="hfp-speed-wrap";let h=document.createElement("button");h.className="hfp-speed-btn",h.type="button",h.textContent="1x",h.setAttribute("aria-label","Playback speed");let u=document.createElement("div");u.className="hfp-speed-menu",u.setAttribute("role","menu");for(let o of r){let l=document.createElement("button");l.className="hfp-speed-option",l.type="button",l.setAttribute("role","menuitem"),l.dataset.speed=String(o),l.textContent=L(o),o===1&&l.classList.add("hfp-active"),u.appendChild(l)}p.appendChild(u),p.appendChild(h),i.appendChild(n),i.appendChild(s),i.appendChild(c),i.appendChild(p),a.appendChild(i);let m=!1,b=null,f=r.indexOf(1);f===-1&&(f=0),n.addEventListener("click",o=>{o.stopPropagation(),m?e.onPause():e.onPlay()});let g=o=>{for(let l of u.querySelectorAll(".hfp-speed-option"))l.classList.toggle("hfp-active",l.dataset.speed===String(o))};h.addEventListener("click",o=>{o.stopPropagation();let l=u.classList.toggle("hfp-open");h.setAttribute("aria-expanded",String(l))}),u.addEventListener("click",o=>{o.stopPropagation();let l=o.target.closest(".hfp-speed-option");if(!l)return;let _=parseFloat(l.dataset.speed);f=r.indexOf(_),h.textContent=L(_),g(_),u.classList.remove("hfp-open"),h.setAttribute("aria-expanded","false"),e.onSpeedChange(_)});let y=()=>{u.classList.remove("hfp-open"),h.setAttribute("aria-expanded","false")};document.addEventListener("click",y);let v=o=>{let l=s.getBoundingClientRect(),_=Math.max(0,Math.min(1,(o-l.left)/l.width));e.onSeek(_)},S=!1;s.addEventListener("mousedown",o=>{o.stopPropagation(),S=!0,v(o.clientX)});let H=o=>{S&&v(o.clientX)},O=()=>{S=!1};document.addEventListener("mousemove",H),document.addEventListener("mouseup",O),s.addEventListener("touchstart",o=>{S=!0;let l=o.touches[0];l&&v(l.clientX)},{passive:!0});let D=o=>{if(S){let l=o.touches[0];l&&v(l.clientX)}},N=()=>{S=!1};document.addEventListener("touchmove",D,{passive:!0}),document.addEventListener("touchend",N);let F=()=>{b&&clearTimeout(b),b=setTimeout(()=>{m&&i.classList.add("hfp-hidden")},3e3)},U=a instanceof ShadowRoot?a.host:a;return U.addEventListener("mousemove",()=>{i.classList.remove("hfp-hidden"),F()}),U.addEventListener("mouseleave",()=>{m&&i.classList.add("hfp-hidden")}),{updateTime(o,l){let _=l>0?o/l*100:0;d.style.width=`${_}%`,c.textContent=`${x(o)} / ${x(l)}`},updatePlaying(o){m=o,n.innerHTML=o?$:k,n.setAttribute("aria-label",o?"Pause":"Play"),o?F():i.classList.remove("hfp-hidden")},updateSpeed(o){let l=r.indexOf(o);l!==-1&&(f=l),h.textContent=L(o),g(o)},show(){i.style.display=""},hide(){i.style.display="none"},destroy(){document.removeEventListener("mousemove",H),document.removeEventListener("mouseup",O),document.removeEventListener("touchmove",D),document.removeEventListener("touchend",N),document.removeEventListener("click",y),b&&clearTimeout(b)}}}function j(a){return a.hasRuntime||a.runtimeInjected?!1:!!(a.hasNestedCompositions||a.hasTimelines&&a.attempts>=5)}var R=null;function Z(){if(R)return R;if(typeof CSSStyleSheet>"u")return null;try{let a=new CSSStyleSheet;return a.replaceSync(A),R=a,a}catch{return null}}var I=30,K="https://cdn.jsdelivr.net/npm/@hyperframes/core/dist/hyperframe.runtime.iife.js",w="shader-capture-scale",E="shader-loading",ee="__hf_shader_capture_scale",te="__hf_shader_loading",M=["Preparing scene transitions","Sampling outgoing scene motion","Sampling incoming scene motion","Caching transition frames","Finalizing transition preview"];function V(a){if(a===null)return null;let e=Number(a);return!Number.isFinite(e)||e<=0?null:String(Math.min(1,Math.max(.25,e)))}function q(a){if(a===null||a.trim()==="")return"composition";let e=a.trim().toLowerCase();return e==="none"||e==="false"||e==="0"||e==="off"?"none":e==="player"||e==="true"||e==="1"||e==="on"?"player":"composition"}function W(a,e,t){t===null?a.delete(e):a.set(e,t)}function re(a,e,t){let r=a.indexOf("#"),i=r>=0?a.slice(0,r):a,n=r>=0?a.slice(r):"",s=i.indexOf("?"),d=s>=0?i.slice(0,s):i,c=s>=0?i.slice(s+1):"",p=new URLSearchParams(c);W(p,ee,e),W(p,te,t==="composition"?null:t);let h=p.toString();return`${d}${h?`?${h}`:""}${n}`}function ie(a,e,t){if(e===null&&t==="composition")return a;let r=[];e!==null&&r.push(`window.__HF_SHADER_CAPTURE_SCALE=${JSON.stringify(e)};`),t!=="composition"&&r.push(`window.__HF_SHADER_LOADING=${JSON.stringify(t)};`);let i=`<script data-hyperframes-player-shader-options>${r.join("")}</script>`;return/<head\b[^>]*>/i.test(a)?a.replace(/<head\b[^>]*>/i,n=>`${n}${i}`):/<html\b[^>]*>/i.test(a)?a.replace(/<html\b[^>]*>/i,n=>`${n}${i}`):`${i}${a}`}var T=class a extends HTMLElement{static get observedAttributes(){return["src","srcdoc","width","height","controls","muted","poster","playback-rate","audio-src",w,E]}shadow;container;iframe;posterEl=null;controlsApi=null;resizeObserver;shaderLoaderEl;shaderLoaderFillEl;shaderLoaderTitleEl;shaderLoaderDetailEl;shaderLoaderTransitionValueEl;shaderLoaderFrameLabelEl;shaderLoaderFrameValueEl;shaderLoaderFrameRowEl;shaderLoaderHideTimeout=null;_ready=!1;_duration=0;_currentTime=0;_paused=!0;_compositionWidth=1920;_compositionHeight=1080;_probeInterval=null;_lastUpdateMs=0;_parentMedia=[];_audioOwner="runtime";_mediaObserver;_playbackErrorPosted=!1;constructor(){super(),this.shadow=this.attachShadow({mode:"open"});let e=Z();if(e)this.shadow.adoptedStyleSheets=[e];else{let r=document.createElement("style");r.textContent=A,this.shadow.appendChild(r)}this.container=document.createElement("div"),this.container.className="hfp-container",this.iframe=document.createElement("iframe"),this.iframe.className="hfp-iframe",this.iframe.sandbox.add("allow-scripts","allow-same-origin"),this.iframe.allow="autoplay; fullscreen",this.iframe.referrerPolicy="no-referrer",this.iframe.title="HyperFrames Composition",this.container.appendChild(this.iframe),this.shadow.appendChild(this.container);let t=this._createShaderLoader();this.shaderLoaderEl=t.root,this.shaderLoaderFillEl=t.fill,this.shaderLoaderTitleEl=t.title,this.shaderLoaderDetailEl=t.detail,this.shaderLoaderTransitionValueEl=t.transitionValue,this.shaderLoaderFrameLabelEl=t.frameLabel,this.shaderLoaderFrameValueEl=t.frameValue,this.shaderLoaderFrameRowEl=t.frameRow,this.shadow.appendChild(this.shaderLoaderEl),this.addEventListener("click",r=>{this._isControlsClick(r)||(this._paused?this.play():this.pause())}),this.resizeObserver=new ResizeObserver(()=>this._updateScale()),this._onMessage=this._onMessage.bind(this),this._onIframeLoad=this._onIframeLoad.bind(this)}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._setupPoster(),this.hasAttribute("audio-src")&&this._setupParentAudioFromUrl(this.getAttribute("audio-src")),this.hasAttribute("srcdoc")&&(this.iframe.srcdoc=this._prepareSrcdoc(this.getAttribute("srcdoc"))),this.hasAttribute("src")&&(this.iframe.src=this._prepareSrc(this.getAttribute("src")))}disconnectedCallback(){this.resizeObserver.disconnect(),window.removeEventListener("message",this._onMessage),this.iframe.removeEventListener("load",this._onIframeLoad),this._probeInterval&&clearInterval(this._probeInterval),this.shaderLoaderHideTimeout&&clearTimeout(this.shaderLoaderHideTimeout),this.shaderLoaderHideTimeout=null,this._teardownMediaObserver(),this.controlsApi?.destroy();for(let e of this._parentMedia)e.el.pause(),e.el.src="";this._parentMedia=[]}attributeChangedCallback(e,t,r){switch(e){case"src":r&&(this._ready=!1,this.iframe.src=this._prepareSrc(r));break;case"srcdoc":this._ready=!1,r!==null?this.iframe.srcdoc=this._prepareSrcdoc(r):this.iframe.removeAttribute("srcdoc");break;case"width":this._compositionWidth=parseInt(r||"1920",10),this._updateScale();break;case"height":this._compositionHeight=parseInt(r||"1080",10),this._updateScale();break;case"controls":r!==null?this._setupControls():(this.controlsApi?.destroy(),this.controlsApi=null);break;case"poster":this._setupPoster();break;case"playback-rate":{let i=parseFloat(r||"1");for(let n of this._parentMedia)n.el.playbackRate=i;this._sendControl("set-playback-rate",{playbackRate:i}),this.controlsApi?.updateSpeed(i),this.dispatchEvent(new Event("ratechange"));break}case"muted":for(let i of this._parentMedia)i.el.muted=r!==null;this._sendControl("set-muted",{muted:r!==null});break;case"audio-src":r&&this._setupParentAudioFromUrl(r);break;case w:case E:this._reloadShaderOptions();break}}get iframeElement(){return this.iframe}play(){this._hidePoster(),this._sendControl("play"),this._audioOwner==="parent"&&this._playParentMedia(),this._paused=!1,this.controlsApi?.updatePlaying(!0),this.dispatchEvent(new Event("play"))}pause(){this._sendControl("pause"),this._audioOwner==="parent"&&this._pauseParentMedia(),this._paused=!0,this.controlsApi?.updatePlaying(!1),this.dispatchEvent(new Event("pause"))}seek(e){if(!this._trySyncSeek(e)){let t=Math.round(e*I);this._sendControl("seek",{frame:t})}if(this._currentTime=e,this._audioOwner==="parent")for(let t of this._parentMedia){let r=e-t.start;r>=0&&r<t.duration&&(t.el.currentTime=r)}this._paused=!0,this.controlsApi?.updatePlaying(!1),this.controlsApi?.updateTime(this._currentTime,this._duration)}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 Number(V(this.getAttribute(w))??"1")}set shaderCaptureScale(e){this.setAttribute(w,String(e))}get shaderLoading(){return q(this.getAttribute(E))}set shaderLoading(e){e==="composition"?this.removeAttribute(E):this.setAttribute(E,e)}get muted(){return this.hasAttribute("muted")}set muted(e){e?this.setAttribute("muted",""):this.removeAttribute("muted")}get loop(){return this.hasAttribute("loop")}set loop(e){e?this.setAttribute("loop",""):this.removeAttribute("loop")}_sendControl(e,t={}){try{this.iframe.contentWindow?.postMessage({source:"hf-parent",type:"control",action:e,...t},"*")}catch{}}_shaderCaptureScaleParam(){return V(this.getAttribute(w))}_shaderLoadingMode(){return q(this.getAttribute(E))}_prepareSrc(e){return re(e,this._shaderCaptureScaleParam(),this._shaderLoadingMode())}_prepareSrcdoc(e){return ie(e,this._shaderCaptureScaleParam(),this._shaderLoadingMode())}_reloadShaderOptions(){if(this._shaderLoadingMode()!=="player"&&this._resetShaderLoader(),this.hasAttribute("srcdoc")){this.iframe.srcdoc=this._prepareSrcdoc(this.getAttribute("srcdoc")||"");return}this.hasAttribute("src")&&(this.iframe.src=this._prepareSrc(this.getAttribute("src")||""))}_createShaderLoader(){let e=document.createElement("div");e.className="hfp-shader-loader",e.setAttribute("role","status"),e.setAttribute("aria-live","polite"),e.setAttribute("aria-label","Preparing scene transitions"),e.setAttribute("data-hyperframes-ignore",""),e.draggable=!1;let t=f=>{f.preventDefault(),f.stopPropagation()};for(let f of["selectstart","dragstart","pointerdown","mousedown","click","dblclick","contextmenu","touchstart"])e.addEventListener(f,t,{capture:!0});let r=document.createElement("div");r.className="hfp-shader-loader-panel",r.draggable=!1;let 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("");let n=document.createElement("div");n.className="hfp-shader-loader-title";let s=document.createElement("span");s.className="hfp-shader-loader-title-text",s.textContent=M[0]||"Preparing scene transitions",n.appendChild(s);let d=document.createElement("div");d.className="hfp-shader-loader-detail",d.textContent="Rendering animated scene samples for shader transitions.";let c=document.createElement("div");c.className="hfp-shader-loader-track",c.setAttribute("aria-hidden","true");let p=document.createElement("div");p.className="hfp-shader-loader-fill",c.appendChild(p);let h=document.createElement("div");h.className="hfp-shader-loader-progress";let u=f=>{let g=document.createElement("div");g.className="hfp-shader-loader-row";let y=document.createElement("span");y.className="hfp-shader-loader-label",y.textContent=f;let v=document.createElement("span");return v.className="hfp-shader-loader-value",g.appendChild(y),g.appendChild(v),h.appendChild(g),{row:g,label:y,value:v}},m=u("transition"),b=u("transition frame");return r.appendChild(i),r.appendChild(n),r.appendChild(d),r.appendChild(c),r.appendChild(h),e.appendChild(r),{root:e,fill:p,title:s,detail:d,transitionValue:m.value,frameLabel:b.label,frameValue:b.value,frameRow:b.row}}_showShaderLoader(){this.shaderLoaderHideTimeout&&(clearTimeout(this.shaderLoaderHideTimeout),this.shaderLoaderHideTimeout=null),this.shaderLoaderEl.classList.remove("hfp-hiding"),this.shaderLoaderEl.classList.add("hfp-visible")}_hideShaderLoader(){if(this.shaderLoaderEl.classList.contains("hfp-hiding")){this.shaderLoaderHideTimeout||this._scheduleShaderLoaderHideCleanup();return}this.shaderLoaderEl.classList.contains("hfp-visible")&&(this.shaderLoaderEl.classList.add("hfp-hiding"),this.shaderLoaderEl.classList.remove("hfp-visible"),this._scheduleShaderLoaderHideCleanup())}_scheduleShaderLoaderHideCleanup(){this.shaderLoaderHideTimeout&&clearTimeout(this.shaderLoaderHideTimeout),this.shaderLoaderHideTimeout=setTimeout(()=>{this.shaderLoaderEl.classList.remove("hfp-hiding"),this.shaderLoaderHideTimeout=null},420)}_resetShaderLoader(){this.shaderLoaderHideTimeout&&(clearTimeout(this.shaderLoaderHideTimeout),this.shaderLoaderHideTimeout=null),this.shaderLoaderEl.classList.remove("hfp-visible","hfp-hiding"),this.shaderLoaderFillEl.style.transform="scaleX(0)",this.shaderLoaderTransitionValueEl.textContent="",this.shaderLoaderFrameValueEl.textContent="",this.shaderLoaderFrameRowEl.style.visibility="hidden"}_updateShaderLoader(e){if(this._shaderLoadingMode()!=="player"){this._resetShaderLoader();return}if(e.ready||!e.loading){this._hideShaderLoader();return}let t=typeof e.progress=="number"&&Number.isFinite(e.progress)?e.progress:0,r=typeof e.total=="number"&&Number.isFinite(e.total)?e.total:0,i=r>0?Math.min(1,Math.max(0,t/r)):0,n=Math.min(M.length-1,Math.floor(i*M.length));this.shaderLoaderTitleEl.textContent=M[n]||"Preparing scene transitions",this.shaderLoaderDetailEl.textContent=e.phase==="cached"?"Loading cached transition frames before playback.":e.phase==="finalizing"?"Uploading transition textures for smooth playback.":"Rendering animated scene samples for shader transitions.",this.shaderLoaderFillEl.style.transform=`scaleX(${i})`,this.shaderLoaderTransitionValueEl.textContent=e.currentTransition!==void 0&&e.transitionTotal!==void 0?`${e.currentTransition}/${e.transitionTotal}`:r>0?`${t}/${r}`:"";let s=e.transitionFrame!==void 0&&e.transitionFrames!==void 0?`${e.transitionFrame}/${e.transitionFrames}`:"";this.shaderLoaderFrameLabelEl.textContent=e.phase==="cached"?"cached transition frames":e.phase==="finalizing"?"finalizing transition frames":"rendering transition frames",this.shaderLoaderFrameValueEl.textContent=s,this.shaderLoaderFrameRowEl.style.visibility=s?"visible":"hidden",this.shaderLoaderEl.setAttribute("aria-valuenow",String(Math.round(i*100))),this._showShaderLoader()}_trySyncSeek(e){try{let r=this.iframe.contentWindow?.__player,i=r?.seek;return typeof i!="function"?!1:(i.call(r,e),!0)}catch{return!1}}_isControlsClick(e){return e.composedPath().some(t=>t instanceof HTMLElement&&t.classList.contains("hfp-controls"))}_onMessage(e){if(e.source!==this.iframe.contentWindow)return;let t=e.data;if(!(!t||t.source!=="hf-preview")){if(t.type==="shader-transition-state"){let r=t.state&&typeof t.state=="object"?t.state:{};this._updateShaderLoader(r),this.dispatchEvent(new CustomEvent("shadertransitionstate",{detail:{compositionId:t.compositionId,state:r}}));return}if(t.type==="state"){this._currentTime=(t.frame??0)/I;let r=!this._paused,i=!t.isPlaying,n=this._duration>0&&this._currentTime>=this._duration&&(r||t.isPlaying);if(n&&this.loop){this._audioOwner==="parent"&&this._pauseParentMedia(),this._paused=i,this.seek(0),this.play();return}this._paused=i,this._audioOwner==="parent"&&(r&&this._paused?this._pauseParentMedia():!r&&!this._paused&&this._playParentMedia(),this._mirrorParentMediaTime(this._currentTime));let s=performance.now();(s-this._lastUpdateMs>100||this._paused!==r)&&(this._lastUpdateMs=s,this.controlsApi?.updateTime(this._currentTime,this._duration),this.controlsApi?.updatePlaying(!this._paused),this.dispatchEvent(new CustomEvent("timeupdate",{detail:{currentTime:this._currentTime}}))),n&&(this._audioOwner==="parent"&&this._pauseParentMedia(),this._paused=!0,this.controlsApi?.updatePlaying(!1),this.dispatchEvent(new Event("ended")))}t.type==="media-autoplay-blocked"&&this._promoteToParentProxy(),t.type==="timeline"&&t.durationInFrames>0&&Number.isFinite(t.durationInFrames)&&(this._duration=t.durationInFrames/I,this.controlsApi?.updateTime(this._currentTime,this._duration)),t.type==="stage-size"&&t.width>0&&t.height>0&&(this._compositionWidth=t.width,this._compositionHeight=t.height,this._updateScale())}}_runtimeInjected=!1;_onIframeLoad(){let e=0;this._runtimeInjected=!1,this._resetShaderLoader();let t=this._audioOwner==="parent";this._audioOwner="runtime",this._playbackErrorPosted=!1,this._pauseParentMedia(),this._teardownMediaObserver(),t&&this.dispatchEvent(new CustomEvent("audioownershipchange",{detail:{owner:"runtime",reason:"iframe-reload"}})),this._probeInterval&&clearInterval(this._probeInterval),this._probeInterval=setInterval(()=>{e++;try{let r=this.iframe.contentWindow;if(!r)return;let i=!!(r.__hf||r.__player),n=!!(r.__timelines&&Object.keys(r.__timelines).length>0),s=!!this.iframe.contentDocument?.querySelector("[data-composition-src]");if(j({hasRuntime:i,hasTimelines:n,hasNestedCompositions:s,runtimeInjected:this._runtimeInjected,attempts:e})){this._injectRuntime();return}if(this._runtimeInjected&&!i)return;let c=(()=>{if(r.__player&&typeof r.__player.getDuration=="function")return r.__player;if(r.__timelines){let p=Object.keys(r.__timelines);if(p.length>0){let h=this.iframe.contentDocument?.querySelector("[data-composition-id]")?.getAttribute("data-composition-id"),u=h&&h in r.__timelines?h:p[p.length-1],m=r.__timelines[u];return{getDuration:()=>m.duration()}}}return null})();if(c&&c.getDuration()>0){clearInterval(this._probeInterval),this._duration=c.getDuration(),this._ready=!0,this.controlsApi?.updateTime(0,this._duration),this.dispatchEvent(new CustomEvent("ready",{detail:{duration:this._duration}}));let h=this.iframe.contentDocument?.querySelector("[data-composition-id]");if(h){let u=parseInt(h.getAttribute("data-width")||"0",10),m=parseInt(h.getAttribute("data-height")||"0",10);u>0&&m>0&&(this._compositionWidth=u,this._compositionHeight=m,this._updateScale())}this._setupParentMedia(),this.hasAttribute("autoplay")&&this.play();return}}catch{}e>=40&&(clearInterval(this._probeInterval),this.dispatchEvent(new CustomEvent("error",{detail:{message:"Composition timeline not found after 8s"}})))},200)}_injectRuntime(){this._runtimeInjected=!0;try{let e=this.iframe.contentDocument;if(!e)return;let t=e.createElement("script");t.src=K,t.onload=()=>{},t.onerror=()=>{},(e.head||e.documentElement).appendChild(t)}catch{}}_updateScale(){let e=this.getBoundingClientRect();if(e.width===0||e.height===0)return;let t=Math.min(e.width/this._compositionWidth,e.height/this._compositionHeight);this.iframe.style.width=`${this._compositionWidth}px`,this.iframe.style.height=`${this._compositionHeight}px`,this.iframe.style.transform=`translate(-50%, -50%) scale(${t})`}_setupControls(){if(this.controlsApi)return;let e={onPlay:()=>this.play(),onPause:()=>this.pause(),onSeek:i=>this.seek(i*this._duration),onSpeedChange:i=>{this.playbackRate=i}},t=this.getAttribute("speed-presets"),r=t?t.split(",").map(Number).filter(i=>!isNaN(i)&&i>0):void 0;this.controlsApi=z(this.shadow,e,{speedPresets:r})}_setupPoster(){let e=this.getAttribute("poster");if(!e){this.posterEl?.remove(),this.posterEl=null;return}this.posterEl||(this.posterEl=document.createElement("img"),this.posterEl.className="hfp-poster",this.shadow.appendChild(this.posterEl)),this.posterEl.src=e}_playParentMedia(){for(let e of this._parentMedia)e.el.src&&e.el.play().catch(t=>this._reportPlaybackError(t))}_reportPlaybackError(e){this._playbackErrorPosted||(this._playbackErrorPosted=!0,this.dispatchEvent(new CustomEvent("playbackerror",{detail:{source:"parent-proxy",error:e}})))}_pauseParentMedia(){for(let e of this._parentMedia)e.el.pause()}static MIRROR_DRIFT_THRESHOLD_SECONDS=.05;static MIRROR_REQUIRED_CONSECUTIVE_DRIFT_SAMPLES=2;_mirrorParentMediaTime(e,t){let r=t?.force===!0,i=a.MIRROR_REQUIRED_CONSECUTIVE_DRIFT_SAMPLES,n=a.MIRROR_DRIFT_THRESHOLD_SECONDS;for(let s of this._parentMedia){let d=e-s.start;if(d<0||d>=s.duration){s.driftSamples=0;continue}Math.abs(s.el.currentTime-d)>n?(s.driftSamples+=1,(r||s.driftSamples>=i)&&(s.el.currentTime=d,s.driftSamples=0)):s.driftSamples=0}}_promoteToParentProxy(){this._audioOwner!=="parent"&&(this._audioOwner="parent",this._sendControl("set-media-output-muted",{muted:!0}),this._mirrorParentMediaTime(this._currentTime,{force:!0}),this._paused||this._playParentMedia(),this.dispatchEvent(new CustomEvent("audioownershipchange",{detail:{owner:"parent",reason:"autoplay-blocked"}})))}_createParentMedia(e,t,r,i){if(this._parentMedia.some(d=>d.el.src===e))return null;let n=t==="video"?document.createElement("video"):new Audio;n.preload="auto",n.src=e,n.load(),n.muted=this.muted,this.playbackRate!==1&&(n.playbackRate=this.playbackRate);let s={el:n,start:r,duration:i,driftSamples:0};return this._parentMedia.push(s),s}_setupParentAudioFromUrl(e){this._createParentMedia(e,"audio",0,1/0)}_setupParentMedia(){try{let e=this.iframe.contentDocument;if(!e)return;let t=e.querySelectorAll("audio[data-start], video[data-start]");for(let r of t)this._adoptIframeMedia(r);this._observeDynamicMedia(e)}catch{}}_adoptIframeMedia(e){let t=e.getAttribute("src")||e.querySelector("source")?.getAttribute("src");if(!t)return;let r=new URL(t,e.ownerDocument.baseURI).href,i=parseFloat(e.getAttribute("data-start")||"0"),n=parseFloat(e.getAttribute("data-duration")||"Infinity"),s=e.tagName==="VIDEO"?"video":"audio",d=this._createParentMedia(r,s,i,n);d&&this._audioOwner==="parent"&&(this._mirrorParentMediaTime(this._currentTime,{force:!0}),!this._paused&&d.el.src&&d.el.play().catch(c=>this._reportPlaybackError(c)))}_observeDynamicMedia(e){if(this._teardownMediaObserver(),typeof MutationObserver>"u"||!e.body)return;let t=new MutationObserver(i=>{for(let n of i){for(let s of n.addedNodes){if(!(s instanceof Element))continue;let d=[];s.matches?.("audio[data-start], video[data-start]")&&d.push(s);let c=s.querySelectorAll?.("audio[data-start], video[data-start]");if(c)for(let p of c)d.push(p);for(let p of d)this._adoptIframeMedia(p)}for(let s of n.removedNodes){if(!(s instanceof Element))continue;let d=[];s.matches?.("audio[data-start], video[data-start]")&&d.push(s);let c=s.querySelectorAll?.("audio[data-start], video[data-start]");if(c)for(let p of c)d.push(p);for(let p of d)this._detachIframeMedia(p)}}}),r=e.querySelectorAll("[data-composition-id]");if(r.length>0)for(let i of r)t.observe(i,{childList:!0,subtree:!0});else t.observe(e.body,{childList:!0,subtree:!0});this._mediaObserver=t}_teardownMediaObserver(){this._mediaObserver?.disconnect(),this._mediaObserver=void 0}_detachIframeMedia(e){let t=e.getAttribute("src")||e.querySelector("source")?.getAttribute("src");if(!t)return;let r=new URL(t,e.ownerDocument.baseURI).href,i=this._parentMedia.findIndex(s=>s.el.src===r);if(i===-1)return;let n=this._parentMedia[i];n.el.pause(),n.el.src="",this._parentMedia.splice(i,1)}_hidePoster(){this.posterEl?.remove(),this.posterEl=null}};customElements.get("hyperframes-player")||customElements.define("hyperframes-player",T);0&&(module.exports={HyperframesPlayer,SPEED_PRESETS,formatSpeed,formatTime});
199
354
  //# sourceMappingURL=hyperframes-player.cjs.map