@tapflowio/relay 0.14.0 → 0.15.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/dist/api/builds.d.ts +35 -0
- package/dist/api/builds.d.ts.map +1 -1
- package/dist/api/builds.js +62 -30
- package/dist/api/builds.js.map +1 -1
- package/dist/lib/config.d.ts.map +1 -1
- package/dist/lib/config.js +18 -4
- package/dist/lib/config.js.map +1 -1
- package/dist/lib/dataDir.d.ts +8 -0
- package/dist/lib/dataDir.d.ts.map +1 -0
- package/dist/lib/dataDir.js +18 -0
- package/dist/lib/dataDir.js.map +1 -0
- package/package.json +4 -4
- package/public/assets/{AppCenter-DbFf7BKA.js → AppCenter-DHKav0MA.js} +2 -2
- package/public/assets/AppCenter-DHKav0MA.js.br +0 -0
- package/public/assets/Default-FOVo8D6L.js +1 -0
- package/public/assets/Default-FOVo8D6L.js.br +0 -0
- package/public/assets/Invite-DdjwJ4DV.js +1 -0
- package/public/assets/Invite-DdjwJ4DV.js.br +0 -0
- package/public/assets/{MacResources-D-j1pG9s.js → MacResources-Dl1w6E1h.js} +2 -2
- package/public/assets/MacResources-Dl1w6E1h.js.br +0 -0
- package/public/assets/{NotFound-BwAREUV8.js → NotFound-BMUavI-G.js} +1 -1
- package/public/assets/NotFound-BMUavI-G.js.br +0 -0
- package/public/assets/{QASession-Du5LOUTZ.js → QASession-BzfWUo9F.js} +6 -6
- package/public/assets/QASession-BzfWUo9F.js.br +0 -0
- package/public/assets/{ResetPassword-C6cya_7-.js → ResetPassword-Yn2hnB_M.js} +1 -1
- package/public/assets/ResetPassword-Yn2hnB_M.js.br +0 -0
- package/public/assets/{Setup-DHS2ZvMu.js → Setup-BaGV0xx6.js} +1 -1
- package/public/assets/Setup-BaGV0xx6.js.br +0 -0
- package/public/assets/{Team-DkIXb37o.js → Team-BOwoos5_.js} +2 -2
- package/public/assets/Team-BOwoos5_.js.br +0 -0
- package/public/assets/Tokens-Bu1FtE_n.js +1 -0
- package/public/assets/Tokens-Bu1FtE_n.js.br +0 -0
- package/public/assets/{alert-dialog-CPQLr1ij.js → alert-dialog-dsCcQ1NM.js} +1 -1
- package/public/assets/alert-dialog-dsCcQ1NM.js.br +0 -0
- package/public/assets/{badge-B63ynAZJ.js → badge-CNtq_oBK.js} +1 -1
- package/public/assets/badge-CNtq_oBK.js.br +0 -0
- package/public/assets/{build-format-CcGvUI_j.js → build-format-D6egYX-U.js} +1 -1
- package/public/assets/build-format-D6egYX-U.js.br +0 -0
- package/public/assets/dialog-Blqnc3tq.js +11 -0
- package/public/assets/dialog-Blqnc3tq.js.br +0 -0
- package/public/assets/index-IvDXNTVd.js +274 -0
- package/public/assets/index-IvDXNTVd.js.br +0 -0
- package/public/assets/{pencil-BAhJ8VF-.js → pencil-CzKUUBmE.js} +1 -1
- package/public/assets/pencil-CzKUUBmE.js.br +0 -0
- package/public/assets/{table-IfQacRqI.js → table-CU0HMyju.js} +1 -1
- package/public/assets/table-CU0HMyju.js.br +0 -0
- package/public/assets/tabs-C9nZOMC5.js +1 -0
- package/public/assets/tabs-C9nZOMC5.js.br +0 -0
- package/public/assets/{trash-2-Bfw6hch4.js → trash-2-Bw_edyHa.js} +1 -1
- package/public/assets/trash-2-Bw_edyHa.js.br +0 -0
- package/public/index.html +1 -1
- package/public/index.html.br +0 -0
- package/public/assets/AppCenter-DbFf7BKA.js.br +0 -0
- package/public/assets/Default-BXiTKHz2.js +0 -1
- package/public/assets/Default-BXiTKHz2.js.br +0 -0
- package/public/assets/Invite-Dw4wdx9j.js +0 -1
- package/public/assets/Invite-Dw4wdx9j.js.br +0 -0
- package/public/assets/MacResources-D-j1pG9s.js.br +0 -0
- package/public/assets/NotFound-BwAREUV8.js.br +0 -2
- package/public/assets/QASession-Du5LOUTZ.js.br +0 -0
- package/public/assets/ResetPassword-C6cya_7-.js.br +0 -0
- package/public/assets/Setup-DHS2ZvMu.js.br +0 -0
- package/public/assets/Team-DkIXb37o.js.br +0 -0
- package/public/assets/Tokens-DxZUmUPI.js +0 -1
- package/public/assets/Tokens-DxZUmUPI.js.br +0 -0
- package/public/assets/alert-dialog-CPQLr1ij.js.br +0 -0
- package/public/assets/badge-B63ynAZJ.js.br +0 -0
- package/public/assets/build-format-CcGvUI_j.js.br +0 -0
- package/public/assets/dialog-CEEdc-Oq.js +0 -11
- package/public/assets/dialog-CEEdc-Oq.js.br +0 -0
- package/public/assets/index-D8ViYmeP.js +0 -274
- package/public/assets/index-D8ViYmeP.js.br +0 -0
- package/public/assets/pencil-BAhJ8VF-.js.br +0 -0
- package/public/assets/table-IfQacRqI.js.br +0 -0
- package/public/assets/tabs-DKQ2XF1o.js +0 -1
- package/public/assets/tabs-DKQ2XF1o.js.br +0 -0
- package/public/assets/trash-2-Bfw6hch4.js.br +0 -0
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{Y as J,a7 as o,am as en,a4 as n,K as q,z as Ct,T as ve,E as we,B as ee,y as Se,S as tn,s as Kn,a9 as at,ae as Fe,ag as Gn,u as
|
|
1
|
+
import{Y as J,a7 as o,am as en,a4 as n,K as q,z as Ct,T as ve,E as we,B as ee,y as Se,S as tn,s as Kn,a9 as at,ae as Fe,ag as Gn,u as Ie,t as bt,Q as nn,N as Ue,ad as qe,ak as qn,U as Jn,x as Zn,g as Qn,af as er,an as tr,al as nr,ac as rr,L as sr}from"./index-IvDXNTVd.js";import{f as or,a as ar,P as rn,c as $t,S as ir,b as cr}from"./build-format-D6egYX-U.js";import{u as sn,T as lr,b as ur,c as Bt,a as zt}from"./tabs-C9nZOMC5.js";import{D as on,a as an,d as dr,e as cn,b as fr,c as hr,k as pr,u as mr,S as gr,i as xr,j as br,g as yr,h as Ot}from"./dialog-Blqnc3tq.js";import{B as vr}from"./badge-CNtq_oBK.js";/**
|
|
2
2
|
* @license lucide-react v0.577.0 - ISC
|
|
3
3
|
*
|
|
4
4
|
* This source code is licensed under the ISC license.
|
|
@@ -53,12 +53,12 @@ import{Y as J,a7 as o,am as en,a4 as n,K as q,z as Ct,T as ve,E as we,B as ee,y
|
|
|
53
53
|
*
|
|
54
54
|
* This source code is licensed under the ISC license.
|
|
55
55
|
* See the LICENSE file in the root directory of this source tree.
|
|
56
|
-
*/const
|
|
56
|
+
*/const Ir=[["path",{d:"M21 12a9 9 0 1 1-6.219-8.56",key:"13zald"}]],pt=J("loader-circle",Ir);/**
|
|
57
57
|
* @license lucide-react v0.577.0 - ISC
|
|
58
58
|
*
|
|
59
59
|
* This source code is licensed under the ISC license.
|
|
60
60
|
* See the LICENSE file in the root directory of this source tree.
|
|
61
|
-
*/const
|
|
61
|
+
*/const $r=[["path",{d:"M22 17a2 2 0 0 1-2 2H6.828a2 2 0 0 0-1.414.586l-2.202 2.202A.71.71 0 0 1 2 21.286V5a2 2 0 0 1 2-2h16a2 2 0 0 1 2 2z",key:"18887p"}]],Br=J("message-square",$r);/**
|
|
62
62
|
* @license lucide-react v0.577.0 - ISC
|
|
63
63
|
*
|
|
64
64
|
* This source code is licensed under the ISC license.
|
|
@@ -93,7 +93,7 @@ import{Y as J,a7 as o,am as en,a4 as n,K as q,z as Ct,T as ve,E as we,B as ee,y
|
|
|
93
93
|
*
|
|
94
94
|
* This source code is licensed under the ISC license.
|
|
95
95
|
* See the LICENSE file in the root directory of this source tree.
|
|
96
|
-
*/const es=[["path",{d:"M11 4.702a.705.705 0 0 0-1.203-.498L6.413 7.587A1.4 1.4 0 0 1 5.416 8H3a1 1 0 0 0-1 1v6a1 1 0 0 0 1 1h2.416a1.4 1.4 0 0 1 .997.413l3.383 3.384A.705.705 0 0 0 11 19.298z",key:"uqj9uw"}],["path",{d:"M16 9a5 5 0 0 1 0 6",key:"1q6k2b"}]],ts=J("volume-1",es);function ns(e){const[t,r]=o.useState(null);return o.useEffect(()=>{e&&or(e).then(r)},[e]),{build:t}}function rs(e){const[t,r]=o.useState([]),[s,a]=o.useState(null),[i,c]=o.useState(null),[h,d]=o.useState(""),[m,p]=o.useState(!1),[g,u]=o.useState(""),y=o.useCallback(D=>{D.type==="agents:listed"&&r(D.sessions),D.type==="session:joined"&&(p(!1),u("Connected")),D.type==="error"&&(p(!1),u(`Error: ${D.message}`))},[]),{send:j,connected:L}=sn(y);o.useEffect(()=>{if(!L)return;j({type:"agents:list"});const D=setInterval(()=>j({type:"agents:list"}),5e3);return()=>clearInterval(D)},[L,j]);const k=o.useRef({sessionId:i,deviceId:h});o.useEffect(()=>{k.current={sessionId:i,deviceId:h}},[i,h]),o.useEffect(()=>()=>{const{sessionId:D,deviceId:B}=k.current;D&&B&&j({type:"device:shutdown",sessionId:D,payload:{deviceId:B}})},[j]);const A=t.filter(D=>D.devices.some(B=>B.platform===e)),C=o.useCallback(D=>{d(D.id),p(!0),u("Booting…"),c(D.sessionId)},[]),P=o.useCallback(()=>d(""),[]),N=o.useCallback(()=>{const{sessionId:D,deviceId:B}=k.current;D&&B&&j({type:"device:shutdown",sessionId:D,payload:{deviceId:B}}),c(null),p(!1),u("")},[j]),F=o.useCallback(()=>{const{sessionId:D,deviceId:B}=k.current;D&&B&&j({type:"device:shutdown",sessionId:D,payload:{deviceId:B}}),c(null),a(null),p(!1),u("")},[j]);return{sessions:t,selectedAgent:s,setSelectedAgent:a,activeSessionId:i,deviceId:h,booting:m,status:g,send:j,connected:L,agentGroups:A,startDevice:C,resetDevice:P,handleBack:N,handleBackToMacs:F}}function ss(e,t){const[r,s]=o.useState(""),[a,i]=o.useState(""),[c,h]=o.useState("app-only"),d=(e==null?void 0:e.devices.filter(g=>g.platform===t))??[],m=[...new Set(d.map(g=>g.osVersion).filter(Boolean))].sort((g,u)=>{const y=k=>k.replace(/^[^\d]*/,"").split(".").map(Number),[j,L]=[y(g),y(u)];for(let k=0;k<Math.max(j.length,L.length);k++){const A=(L[k]??0)-(j[k]??0);if(A!==0)return A}return 0}),p=(r?d.filter(g=>g.osVersion===r):d).filter(g=>!a||g.name.toLowerCase().includes(a.toLowerCase()));return{filteredDevices:d,osVersions:m,osVersion:r,setOsVersion:s,deviceSearch:a,setDeviceSearch:i,versionedDevices:p,resetMode:c,setResetMode:h}}function os(){const[e]=en(),t=e.get("perf")==="1",[r,s]=o.useState(t);return o.useEffect(()=>{if(!t){s(!1);return}s(!0);const a=i=>{i.ctrlKey&&i.shiftKey&&i.key==="P"&&s(c=>!c)};return window.addEventListener("keydown",a),()=>window.removeEventListener("keydown",a)},[t]),{perfMode:t,visible:r}}const as=["video/mp4;codecs=avc1","video/webm;codecs=vp9","video/webm;codecs=vp8","video/webm"];function dn({sessionId:e,buildId:t,onRecordingUploaded:r}){const[s,a]=o.useState("idle"),i=o.useRef(null),c=o.useRef(r);o.useEffect(()=>{c.current=r},[r]);const h=o.useRef(!1),d=o.useRef(null),m=o.useRef([]),p=o.useRef(""),g=o.useRef(0),u=o.useRef(null),y=o.useCallback(()=>{var k;h.current&&((k=u.current)==null||k.call(u),g.current=requestAnimationFrame(y))},[]),j=o.useCallback(k=>{const A=i.current;if(!A)return;const C=A.getContext("2d");C&&(C.fillStyle="#000",C.fillRect(0,0,A.width,A.height));const P=as.find(F=>MediaRecorder.isTypeSupported(F))??"";if(!P)return;p.current=P,m.current=[];const N=new MediaRecorder(A.captureStream(30),{mimeType:P});N.ondataavailable=F=>{F.data.size>0&&m.current.push(F.data)},d.current=N,N.start(1e3),u.current=k,h.current=!0,g.current=requestAnimationFrame(y),a("recording")},[y]),L=o.useCallback(async()=>{var F;a("uploading"),h.current=!1,cancelAnimationFrame(g.current);const k=d.current;if(!k){a("idle");return}await new Promise(D=>{const B=setTimeout(D,5e3);k.onstop=()=>{clearTimeout(B),D()};try{k.stop()}catch{clearTimeout(B),D()}}),d.current=null;const A=p.current,C=A.includes("mp4")?".mp4":".webm",P=new Blob(m.current,{type:A});m.current=[];const N=new FormData;N.append("file",P,`tapflow-${Date.now()}${C}`);try{const D=new URLSearchParams({sessionId:e});t&&D.set("buildId",String(t));const B=await fetch(`/api/v1/recordings/upload?${D}`,{method:"POST",credentials:"include",body:N}),X=await B.json();if(B.ok&&X.url){const $=document.createElement("a");$.href=X.url,$.download="",$.click(),(F=c.current)==null||F.call(c),a("done"),setTimeout(()=>a("idle"),2e3)}else a("idle")}catch{a("idle")}},[e,t]);return o.useEffect(()=>{if(s!=="recording")return;const k=()=>{document.visibilityState==="hidden"&&L()};return document.addEventListener("visibilitychange",k),()=>{var A;document.removeEventListener("visibilitychange",k),h.current&&(h.current=!1,cancelAnimationFrame(g.current),(A=d.current)==null||A.stop(),d.current=null)}},[s,L]),{recordState:s,recordCanvasRef:i,startClientRecording:j,stopClientRecording:L}}function fn(){const e=o.useRef(0),[t,r]=o.useState(0);return o.useEffect(()=>{const s=setInterval(()=>{r(e.current),e.current=0},1e3);return()=>clearInterval(s)},[]),{fps:t,frameCount:e}}function Ge({className:e,...t}){return n.jsx("kbd",{"data-slot":"kbd",className:q("bg-muted text-muted-foreground pointer-events-none inline-flex h-5 w-fit min-w-5 select-none items-center justify-center gap-1 rounded-sm px-1 font-sans text-xs font-medium","[&_svg:not([class*='size-'])]:size-3","[[data-slot=tooltip-content]_&]:bg-background/20 [[data-slot=tooltip-content]_&]:text-background dark:[[data-slot=tooltip-content]_&]:bg-background/10",e),...t})}function Et({className:e,...t}){return n.jsx("kbd",{"data-slot":"kbd-group",className:q("inline-flex items-center gap-1",e),...t})}function rt({label:e,keys:t}){return n.jsxs("span",{className:"flex items-center gap-3",children:[e,n.jsx(Et,{children:t.map(r=>n.jsx(Ge,{children:r},r))})]})}function hn({joined:e,onScreenshot:t,onRecordToggle:r,recordState:s,onRotate:a,onDeepLink:i,platformSlot:c,launchSlot:h}){return e?n.jsx(Ct,{delayDuration:400,children:n.jsxs("div",{className:"flex flex-col items-center gap-0.5 rounded-2xl border bg-background/90 backdrop-blur-sm px-1.5 py-2.5 shrink-0 mt-3",children:[h,c,n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:i,children:n.jsx(un,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsx(rt,{label:"Deeplink",keys:["⌘","K"]})})]}),n.jsx("div",{className:"w-4 h-px bg-border my-1"}),n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:t,children:n.jsx(Cr,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsx(rt,{label:"Screenshot",keys:["⌘","S"]})})]}),n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:q("h-8 w-8",s==="recording"&&"text-red-500 hover:text-red-500"),disabled:s==="uploading"||s==="done",onClick:r,children:s==="uploading"?n.jsx(pt,{className:"h-4 w-4 animate-spin"}):s==="recording"?n.jsx(Gr,{className:"h-4 w-4 fill-current"}):n.jsx(Jr,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:s==="idle"?n.jsx(rt,{label:"Start recording",keys:["⌘","⇧","Y"]}):s==="recording"?n.jsx(rt,{label:"Stop recording",keys:["⌘","⇧","Y"]}):"Processing…"})]}),n.jsx("div",{className:"w-4 h-px bg-border my-1"}),n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:a,children:n.jsx(Vr,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsx(rt,{label:"Rotate",keys:["⌘","⇧","O"]})})]})]})}):null}class Nt{constructor(t){this.bytes=t,this.bitPos=0}get position(){return this.bitPos}bit(){const t=this.bitPos>>3,r=7-(this.bitPos&7);return this.bitPos++,t>=this.bytes.length?0:this.bytes[t]>>r&1}bits(t){let r=0;for(let s=0;s<t;s++)r=r<<1|this.bit();return r>>>0}flag(){return this.bit()===1}ue(){let t=0;for(;this.bit()===0&&t<32;)t++;return t===0?0:(1<<t)-1+this.bits(t)}se(){const t=this.ue();return t&1?Math.ceil(t/2):-Math.ceil(t/2)}}class is{constructor(){this.bitsArr=[]}bit(t){this.bitsArr.push(t&1)}ue(t){const r=t+1,s=Math.floor(Math.log2(r));for(let a=0;a<s;a++)this.bit(0);for(let a=s;a>=0;a--)this.bit(r>>a&1)}toBytes(){const t=[];for(let r=0;r<this.bitsArr.length;r+=8){let s=0;for(let a=0;a<8;a++)s=s<<1|(this.bitsArr[r+a]??0);t.push(s)}return new Uint8Array(t)}}function pn(e){const t=[];let r=0;for(let s=1;s<e.length;s++){const a=e[s];if(r>=2&&a===3){r=0;continue}t.push(a),r=a===0?r+1:0}return new Uint8Array(t)}function cs(e){const t=[];let r=0;for(const s of e)r>=2&&s<=3&&(t.push(3),r=0),t.push(s),r=s===0?r+1:0;return new Uint8Array(t)}const ls=new Set([100,110,122,244,44,83,86,118,128,138,139,134,135]);function Wt(e){const t=e.ue()+1;e.bits(4),e.bits(4);for(let r=0;r<t;r++)e.ue(),e.ue(),e.flag();e.bits(5),e.bits(5),e.bits(5),e.bits(5)}function mn(e){const t=e.bits(8);e.bits(8);const r=e.bits(8);if(e.ue(),ls.has(t)){const g=e.ue();if(g===3&&e.flag(),e.ue(),e.ue(),e.flag(),e.flag()){const u=g!==3?8:12;for(let y=0;y<u;y++)if(e.flag()){const j=y<6?16:64;let L=8,k=8;for(let A=0;A<j;A++)k!==0&&(k=(L+e.se()+256)%256),L=k===0?L:k}}}e.ue();const s=e.ue();if(s===0)e.ue();else if(s===1){e.flag(),e.se(),e.se();const g=e.ue();for(let u=0;u<g;u++)e.se()}const a=e.ue();e.flag(),e.ue(),e.ue(),e.flag()||e.flag(),e.flag(),e.flag()&&(e.ue(),e.ue(),e.ue(),e.ue());const i={profileIdc:t,levelIdc:r,numRefFrames:a,bitstreamRestriction:!1,maxNumReorderFrames:null,maxDecFrameBuffering:null};if(!e.flag())return{...i,vuiPresent:!1,restrictionFlagPos:-1};e.flag()&&e.bits(8)===255&&(e.bits(16),e.bits(16)),e.flag()&&e.flag(),e.flag()&&(e.bits(3),e.flag(),e.flag()&&(e.bits(8),e.bits(8),e.bits(8))),e.flag()&&(e.ue(),e.ue()),e.flag()&&(e.bits(32),e.bits(32),e.flag());const h=e.flag();h&&Wt(e);const d=e.flag();d&&Wt(e),(h||d)&&e.flag(),e.flag();const m=e.position;return e.flag()?(e.flag(),e.ue(),e.ue(),e.ue(),e.ue(),{...i,vuiPresent:!0,bitstreamRestriction:!0,maxNumReorderFrames:e.ue(),maxDecFrameBuffering:e.ue(),restrictionFlagPos:m}):{...i,vuiPresent:!0,restrictionFlagPos:m}}function us(e){const t=mn(new Nt(pn(e)));return{profileIdc:t.profileIdc,levelIdc:t.levelIdc,vuiPresent:t.vuiPresent,bitstreamRestriction:t.bitstreamRestriction,maxNumReorderFrames:t.maxNumReorderFrames,maxDecFrameBuffering:t.maxDecFrameBuffering}}function ds(e){const t=pn(e),r=mn(new Nt(t));if(!r.vuiPresent||r.restrictionFlagPos<0||r.bitstreamRestriction)return null;const s=new is,a=new Nt(t);for(let i=0;i<r.restrictionFlagPos;i++)s.bit(a.bit());return s.bit(1),s.bit(1),s.ue(0),s.ue(0),s.ue(0),s.ue(0),s.ue(0),s.ue(r.numRefFrames),s.bit(1),Uint8Array.from([e[0],...cs(s.toBytes())])}function fs(e){const t=[],r=e.length;let s=-1,a=0;for(;a+2<r;){const i=a+3<r&&e[a]===0&&e[a+1]===0&&e[a+2]===0&&e[a+3]===1,c=e[a]===0&&e[a+1]===0&&e[a+2]===1;i||c?(s>=0&&t.push(e.subarray(s,a)),a+=i?4:3,s=a):a++}return s>=0&&t.push(e.subarray(s,r)),t}class hs{constructor(t){this.onFrame=t,this.decoder=null,this.sps=null,this.pps=null,this.frameCount=0,this.submitAt=new Map,this.spsLogged=!1}setDecodeSampler(t){this.decodeSampler=t}decode(t){const r=[];let s=!1;for(const m of fs(new Uint8Array(t))){const p=m[0]&31;if(p===7){const g=!this.sps||m.length!==this.sps.length||m.some((u,y)=>u!==this.sps[y]);this.sps=m,g&&this.decoder&&(this.decoder.close(),this.decoder=null)}else p===8?this.pps=m:p>=1&&p<=5&&(p===5&&(s=!0),r.push(m))}if(s&&this.sps&&this.pps&&!this.decoder&&this.initDecoder(this.sps,this.pps),!this.decoder||r.length===0)return;let a=0;for(const m of r)a+=4+m.length;const i=new Uint8Array(a),c=new DataView(i.buffer);let h=0;for(const m of r)c.setUint32(h,m.length,!1),h+=4,i.set(m,h),h+=m.length;const d=Math.round(this.frameCount++*(1e6/30));if(this.decodeSampler&&(this.submitAt.set(d,performance.now()),this.submitAt.size>120)){const m=this.submitAt.keys().next().value;m!==void 0&&this.submitAt.delete(m)}try{this.decoder.decode(new EncodedVideoChunk({type:s?"key":"delta",timestamp:d,data:i}))}catch{}}sampleDecode(t){var s;if(!this.decodeSampler)return;const r=this.submitAt.get(t.timestamp);r!==void 0&&(this.submitAt.delete(t.timestamp),this.decodeSampler({decodeMs:performance.now()-r,queueSize:((s=this.decoder)==null?void 0:s.decodeQueueSize)??0}))}close(){var t;(t=this.decoder)==null||t.close(),this.decoder=null}logSpsVui(t){if(!(this.spsLogged||!this.decodeSampler)){this.spsLogged=!0;try{console.log("[sps-vui]",JSON.stringify(us(t)))}catch(r){console.warn("[sps-vui] parse failed",r)}}}initDecoder(t,r){this.logSpsVui(t);const s=ds(t)??t,a=s[0]===0?s.subarray(4):s,i=`avc1.${a[1].toString(16).padStart(2,"0")}${a[2].toString(16).padStart(2,"0")}${a[3].toString(16).padStart(2,"0")}`,c=this.buildAVCC(s,r);this.decoder=new VideoDecoder({output:h=>{this.sampleDecode(h),this.onFrame(h)},error:h=>console.error("[WebCodecsCore]",h)}),this.decoder.configure({codec:i,description:c,optimizeForLatency:!0})}buildAVCC(t,r){const s=t[0]===0?t.subarray(4):t,a=r[0]===0?r.subarray(4):r,i=new Uint8Array(8+s.length+1+2+a.length);let c=0;return i[c++]=1,i[c++]=s[1],i[c++]=s[2],i[c++]=s[3],i[c++]=255,i[c++]=225,i[c++]=s.length>>8&255,i[c++]=s.length&255,i.set(s,c),c+=s.length,i[c++]=1,i[c++]=a.length>>8&255,i[c++]=a.length&255,i.set(a,c),i}}const ps=`#version 300 es
|
|
96
|
+
*/const es=[["path",{d:"M11 4.702a.705.705 0 0 0-1.203-.498L6.413 7.587A1.4 1.4 0 0 1 5.416 8H3a1 1 0 0 0-1 1v6a1 1 0 0 0 1 1h2.416a1.4 1.4 0 0 1 .997.413l3.383 3.384A.705.705 0 0 0 11 19.298z",key:"uqj9uw"}],["path",{d:"M16 9a5 5 0 0 1 0 6",key:"1q6k2b"}]],ts=J("volume-1",es);function ns(e){const[t,r]=o.useState(null);return o.useEffect(()=>{e&&or(e).then(r)},[e]),{build:t}}function rs(e){const[t,r]=o.useState([]),[s,a]=o.useState(null),[i,c]=o.useState(null),[h,d]=o.useState(""),[m,p]=o.useState(!1),[x,u]=o.useState(""),b=o.useCallback(D=>{D.type==="agents:listed"&&r(D.sessions),D.type==="session:joined"&&(p(!1),u("Connected")),D.type==="error"&&(p(!1),u(`Error: ${D.message}`))},[]),{send:k,connected:L}=sn(b);o.useEffect(()=>{if(!L)return;k({type:"agents:list"});const D=setInterval(()=>k({type:"agents:list"}),5e3);return()=>clearInterval(D)},[L,k]);const C=o.useRef({sessionId:i,deviceId:h});o.useEffect(()=>{C.current={sessionId:i,deviceId:h}},[i,h]),o.useEffect(()=>()=>{const{sessionId:D,deviceId:B}=C.current;D&&B&&k({type:"device:shutdown",sessionId:D,payload:{deviceId:B}})},[k]);const N=t.filter(D=>D.devices.some(B=>B.platform===e)),j=o.useCallback(D=>{d(D.id),p(!0),u("Booting…"),c(D.sessionId)},[]),A=o.useCallback(()=>d(""),[]),_=o.useCallback(()=>{const{sessionId:D,deviceId:B}=C.current;D&&B&&k({type:"device:shutdown",sessionId:D,payload:{deviceId:B}}),c(null),p(!1),u("")},[k]),F=o.useCallback(()=>{const{sessionId:D,deviceId:B}=C.current;D&&B&&k({type:"device:shutdown",sessionId:D,payload:{deviceId:B}}),c(null),a(null),p(!1),u("")},[k]);return{sessions:t,selectedAgent:s,setSelectedAgent:a,activeSessionId:i,deviceId:h,booting:m,status:x,send:k,connected:L,agentGroups:N,startDevice:j,resetDevice:A,handleBack:_,handleBackToMacs:F}}function ss(e,t){const[r,s]=o.useState(""),[a,i]=o.useState(""),[c,h]=o.useState("app-only"),d=(e==null?void 0:e.devices.filter(x=>x.platform===t))??[],m=[...new Set(d.map(x=>x.osVersion).filter(Boolean))].sort((x,u)=>{const b=C=>C.replace(/^[^\d]*/,"").split(".").map(Number),[k,L]=[b(x),b(u)];for(let C=0;C<Math.max(k.length,L.length);C++){const N=(L[C]??0)-(k[C]??0);if(N!==0)return N}return 0}),p=(r?d.filter(x=>x.osVersion===r):d).filter(x=>!a||x.name.toLowerCase().includes(a.toLowerCase()));return{filteredDevices:d,osVersions:m,osVersion:r,setOsVersion:s,deviceSearch:a,setDeviceSearch:i,versionedDevices:p,resetMode:c,setResetMode:h}}function os(){const[e]=en(),t=e.get("perf")==="1",[r,s]=o.useState(t);return o.useEffect(()=>{if(!t){s(!1);return}s(!0);const a=i=>{i.ctrlKey&&i.shiftKey&&i.key==="P"&&s(c=>!c)};return window.addEventListener("keydown",a),()=>window.removeEventListener("keydown",a)},[t]),{perfMode:t,visible:r}}const as=["video/mp4;codecs=avc1","video/webm;codecs=vp9","video/webm;codecs=vp8","video/webm"];function dn({sessionId:e,buildId:t,onRecordingUploaded:r}){const[s,a]=o.useState("idle"),i=o.useRef(null),c=o.useRef(r);o.useEffect(()=>{c.current=r},[r]);const h=o.useRef(!1),d=o.useRef(null),m=o.useRef([]),p=o.useRef(""),x=o.useRef(0),u=o.useRef(null),b=o.useCallback(()=>{var C;h.current&&((C=u.current)==null||C.call(u),x.current=requestAnimationFrame(b))},[]),k=o.useCallback(C=>{const N=i.current;if(!N)return;const j=N.getContext("2d");j&&(j.fillStyle="#000",j.fillRect(0,0,N.width,N.height));const A=as.find(F=>MediaRecorder.isTypeSupported(F))??"";if(!A)return;p.current=A,m.current=[];const _=new MediaRecorder(N.captureStream(30),{mimeType:A});_.ondataavailable=F=>{F.data.size>0&&m.current.push(F.data)},d.current=_,_.start(1e3),u.current=C,h.current=!0,x.current=requestAnimationFrame(b),a("recording")},[b]),L=o.useCallback(async()=>{var F;a("uploading"),h.current=!1,cancelAnimationFrame(x.current);const C=d.current;if(!C){a("idle");return}await new Promise(D=>{const B=setTimeout(D,5e3);C.onstop=()=>{clearTimeout(B),D()};try{C.stop()}catch{clearTimeout(B),D()}}),d.current=null;const N=p.current,j=N.includes("mp4")?".mp4":".webm",A=new Blob(m.current,{type:N});m.current=[];const _=new FormData;_.append("file",A,`tapflow-${Date.now()}${j}`);try{const D=new URLSearchParams({sessionId:e});t&&D.set("buildId",String(t));const B=await fetch(`/api/v1/recordings/upload?${D}`,{method:"POST",credentials:"include",body:_}),X=await B.json();if(B.ok&&X.url){const I=document.createElement("a");I.href=X.url,I.download="",I.click(),(F=c.current)==null||F.call(c),a("done"),setTimeout(()=>a("idle"),2e3)}else a("idle")}catch{a("idle")}},[e,t]);return o.useEffect(()=>{if(s!=="recording")return;const C=()=>{document.visibilityState==="hidden"&&L()};return document.addEventListener("visibilitychange",C),()=>{var N;document.removeEventListener("visibilitychange",C),h.current&&(h.current=!1,cancelAnimationFrame(x.current),(N=d.current)==null||N.stop(),d.current=null)}},[s,L]),{recordState:s,recordCanvasRef:i,startClientRecording:k,stopClientRecording:L}}function fn(){const e=o.useRef(0),[t,r]=o.useState(0);return o.useEffect(()=>{const s=setInterval(()=>{r(e.current),e.current=0},1e3);return()=>clearInterval(s)},[]),{fps:t,frameCount:e}}function Ge({className:e,...t}){return n.jsx("kbd",{"data-slot":"kbd",className:q("bg-muted text-muted-foreground pointer-events-none inline-flex h-5 w-fit min-w-5 select-none items-center justify-center gap-1 rounded-sm px-1 font-sans text-xs font-medium","[&_svg:not([class*='size-'])]:size-3","[[data-slot=tooltip-content]_&]:bg-background/20 [[data-slot=tooltip-content]_&]:text-background dark:[[data-slot=tooltip-content]_&]:bg-background/10",e),...t})}function Et({className:e,...t}){return n.jsx("kbd",{"data-slot":"kbd-group",className:q("inline-flex items-center gap-1",e),...t})}function rt({label:e,keys:t}){return n.jsxs("span",{className:"flex items-center gap-3",children:[e,n.jsx(Et,{children:t.map(r=>n.jsx(Ge,{children:r},r))})]})}function hn({joined:e,onScreenshot:t,onRecordToggle:r,recordState:s,onRotate:a,onDeepLink:i,platformSlot:c,launchSlot:h}){return e?n.jsx(Ct,{delayDuration:400,children:n.jsxs("div",{className:"flex flex-col items-center gap-0.5 rounded-2xl border bg-background/90 backdrop-blur-sm px-1.5 py-2.5 shrink-0 mt-3",children:[h,c,n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:i,children:n.jsx(un,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsx(rt,{label:"Deeplink",keys:["⌘","K"]})})]}),n.jsx("div",{className:"w-4 h-px bg-border my-1"}),n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:t,children:n.jsx(Cr,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsx(rt,{label:"Screenshot",keys:["⌘","S"]})})]}),n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:q("h-8 w-8",s==="recording"&&"text-red-500 hover:text-red-500"),disabled:s==="uploading"||s==="done",onClick:r,children:s==="uploading"?n.jsx(pt,{className:"h-4 w-4 animate-spin"}):s==="recording"?n.jsx(Gr,{className:"h-4 w-4 fill-current"}):n.jsx(Jr,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:s==="idle"?n.jsx(rt,{label:"Start recording",keys:["⌘","⇧","Y"]}):s==="recording"?n.jsx(rt,{label:"Stop recording",keys:["⌘","⇧","Y"]}):"Processing…"})]}),n.jsx("div",{className:"w-4 h-px bg-border my-1"}),n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:a,children:n.jsx(Vr,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsx(rt,{label:"Rotate",keys:["⌘","⇧","O"]})})]})]})}):null}class Nt{constructor(t){this.bytes=t,this.bitPos=0}get position(){return this.bitPos}bit(){const t=this.bitPos>>3,r=7-(this.bitPos&7);return this.bitPos++,t>=this.bytes.length?0:this.bytes[t]>>r&1}bits(t){let r=0;for(let s=0;s<t;s++)r=r<<1|this.bit();return r>>>0}flag(){return this.bit()===1}ue(){let t=0;for(;this.bit()===0&&t<32;)t++;return t===0?0:(1<<t)-1+this.bits(t)}se(){const t=this.ue();return t&1?Math.ceil(t/2):-Math.ceil(t/2)}}class is{constructor(){this.bitsArr=[]}bit(t){this.bitsArr.push(t&1)}ue(t){const r=t+1,s=Math.floor(Math.log2(r));for(let a=0;a<s;a++)this.bit(0);for(let a=s;a>=0;a--)this.bit(r>>a&1)}toBytes(){const t=[];for(let r=0;r<this.bitsArr.length;r+=8){let s=0;for(let a=0;a<8;a++)s=s<<1|(this.bitsArr[r+a]??0);t.push(s)}return new Uint8Array(t)}}function pn(e){const t=[];let r=0;for(let s=1;s<e.length;s++){const a=e[s];if(r>=2&&a===3){r=0;continue}t.push(a),r=a===0?r+1:0}return new Uint8Array(t)}function cs(e){const t=[];let r=0;for(const s of e)r>=2&&s<=3&&(t.push(3),r=0),t.push(s),r=s===0?r+1:0;return new Uint8Array(t)}const ls=new Set([100,110,122,244,44,83,86,118,128,138,139,134,135]);function Wt(e){const t=e.ue()+1;e.bits(4),e.bits(4);for(let r=0;r<t;r++)e.ue(),e.ue(),e.flag();e.bits(5),e.bits(5),e.bits(5),e.bits(5)}function mn(e){const t=e.bits(8);e.bits(8);const r=e.bits(8);if(e.ue(),ls.has(t)){const x=e.ue();if(x===3&&e.flag(),e.ue(),e.ue(),e.flag(),e.flag()){const u=x!==3?8:12;for(let b=0;b<u;b++)if(e.flag()){const k=b<6?16:64;let L=8,C=8;for(let N=0;N<k;N++)C!==0&&(C=(L+e.se()+256)%256),L=C===0?L:C}}}e.ue();const s=e.ue();if(s===0)e.ue();else if(s===1){e.flag(),e.se(),e.se();const x=e.ue();for(let u=0;u<x;u++)e.se()}const a=e.ue();e.flag(),e.ue(),e.ue(),e.flag()||e.flag(),e.flag(),e.flag()&&(e.ue(),e.ue(),e.ue(),e.ue());const i={profileIdc:t,levelIdc:r,numRefFrames:a,bitstreamRestriction:!1,maxNumReorderFrames:null,maxDecFrameBuffering:null};if(!e.flag())return{...i,vuiPresent:!1,restrictionFlagPos:-1};e.flag()&&e.bits(8)===255&&(e.bits(16),e.bits(16)),e.flag()&&e.flag(),e.flag()&&(e.bits(3),e.flag(),e.flag()&&(e.bits(8),e.bits(8),e.bits(8))),e.flag()&&(e.ue(),e.ue()),e.flag()&&(e.bits(32),e.bits(32),e.flag());const h=e.flag();h&&Wt(e);const d=e.flag();d&&Wt(e),(h||d)&&e.flag(),e.flag();const m=e.position;return e.flag()?(e.flag(),e.ue(),e.ue(),e.ue(),e.ue(),{...i,vuiPresent:!0,bitstreamRestriction:!0,maxNumReorderFrames:e.ue(),maxDecFrameBuffering:e.ue(),restrictionFlagPos:m}):{...i,vuiPresent:!0,restrictionFlagPos:m}}function us(e){const t=mn(new Nt(pn(e)));return{profileIdc:t.profileIdc,levelIdc:t.levelIdc,vuiPresent:t.vuiPresent,bitstreamRestriction:t.bitstreamRestriction,maxNumReorderFrames:t.maxNumReorderFrames,maxDecFrameBuffering:t.maxDecFrameBuffering}}function ds(e){const t=pn(e),r=mn(new Nt(t));if(!r.vuiPresent||r.restrictionFlagPos<0||r.bitstreamRestriction)return null;const s=new is,a=new Nt(t);for(let i=0;i<r.restrictionFlagPos;i++)s.bit(a.bit());return s.bit(1),s.bit(1),s.ue(0),s.ue(0),s.ue(0),s.ue(0),s.ue(0),s.ue(r.numRefFrames),s.bit(1),Uint8Array.from([e[0],...cs(s.toBytes())])}function fs(e){const t=[],r=e.length;let s=-1,a=0;for(;a+2<r;){const i=a+3<r&&e[a]===0&&e[a+1]===0&&e[a+2]===0&&e[a+3]===1,c=e[a]===0&&e[a+1]===0&&e[a+2]===1;i||c?(s>=0&&t.push(e.subarray(s,a)),a+=i?4:3,s=a):a++}return s>=0&&t.push(e.subarray(s,r)),t}class hs{constructor(t){this.onFrame=t,this.decoder=null,this.sps=null,this.pps=null,this.frameCount=0,this.submitAt=new Map,this.spsLogged=!1}setDecodeSampler(t){this.decodeSampler=t}decode(t){const r=[];let s=!1;for(const m of fs(new Uint8Array(t))){const p=m[0]&31;if(p===7){const x=!this.sps||m.length!==this.sps.length||m.some((u,b)=>u!==this.sps[b]);this.sps=m,x&&this.decoder&&(this.decoder.close(),this.decoder=null)}else p===8?this.pps=m:p>=1&&p<=5&&(p===5&&(s=!0),r.push(m))}if(s&&this.sps&&this.pps&&!this.decoder&&this.initDecoder(this.sps,this.pps),!this.decoder||r.length===0)return;let a=0;for(const m of r)a+=4+m.length;const i=new Uint8Array(a),c=new DataView(i.buffer);let h=0;for(const m of r)c.setUint32(h,m.length,!1),h+=4,i.set(m,h),h+=m.length;const d=Math.round(this.frameCount++*(1e6/30));if(this.decodeSampler&&(this.submitAt.set(d,performance.now()),this.submitAt.size>120)){const m=this.submitAt.keys().next().value;m!==void 0&&this.submitAt.delete(m)}try{this.decoder.decode(new EncodedVideoChunk({type:s?"key":"delta",timestamp:d,data:i}))}catch{}}sampleDecode(t){var s;if(!this.decodeSampler)return;const r=this.submitAt.get(t.timestamp);r!==void 0&&(this.submitAt.delete(t.timestamp),this.decodeSampler({decodeMs:performance.now()-r,queueSize:((s=this.decoder)==null?void 0:s.decodeQueueSize)??0}))}close(){var t;(t=this.decoder)==null||t.close(),this.decoder=null}logSpsVui(t){if(!(this.spsLogged||!this.decodeSampler)){this.spsLogged=!0;try{console.log("[sps-vui]",JSON.stringify(us(t)))}catch(r){console.warn("[sps-vui] parse failed",r)}}}initDecoder(t,r){this.logSpsVui(t);const s=ds(t)??t,a=s[0]===0?s.subarray(4):s,i=`avc1.${a[1].toString(16).padStart(2,"0")}${a[2].toString(16).padStart(2,"0")}${a[3].toString(16).padStart(2,"0")}`,c=this.buildAVCC(s,r);this.decoder=new VideoDecoder({output:h=>{this.sampleDecode(h),this.onFrame(h)},error:h=>console.error("[WebCodecsCore]",h)}),this.decoder.configure({codec:i,description:c,optimizeForLatency:!0})}buildAVCC(t,r){const s=t[0]===0?t.subarray(4):t,a=r[0]===0?r.subarray(4):r,i=new Uint8Array(8+s.length+1+2+a.length);let c=0;return i[c++]=1,i[c++]=s[1],i[c++]=s[2],i[c++]=s[3],i[c++]=255,i[c++]=225,i[c++]=s.length>>8&255,i[c++]=s.length&255,i.set(s,c),c+=s.length,i[c++]=1,i[c++]=a.length>>8&255,i[c++]=a.length&255,i.set(a,c),i}}const ps=`#version 300 es
|
|
97
97
|
in vec2 a_pos;
|
|
98
98
|
out vec2 v_uv;
|
|
99
99
|
void main() {
|
|
@@ -106,7 +106,7 @@ uniform sampler2D u_tex;
|
|
|
106
106
|
out vec4 out_color;
|
|
107
107
|
void main() {
|
|
108
108
|
out_color = texture(u_tex, v_uv);
|
|
109
|
-
}`;function gs(e){const t=e.getContext("webgl2",{alpha:!1,antialias:!1,powerPreference:"high-performance",preserveDrawingBuffer:!0});if(!t)return null;const r=(p,
|
|
109
|
+
}`;function gs(e){const t=e.getContext("webgl2",{alpha:!1,antialias:!1,powerPreference:"high-performance",preserveDrawingBuffer:!0});if(!t)return null;const r=(p,x)=>{const u=t.createShader(p);return t.shaderSource(u,x),t.compileShader(u),u},s=t.createProgram(),a=r(t.VERTEX_SHADER,ps),i=r(t.FRAGMENT_SHADER,ms);t.attachShader(s,a),t.attachShader(s,i),t.linkProgram(s),t.deleteShader(a),t.deleteShader(i),t.useProgram(s);const c=t.createVertexArray();t.bindVertexArray(c);const h=t.createBuffer();t.bindBuffer(t.ARRAY_BUFFER,h),t.bufferData(t.ARRAY_BUFFER,new Float32Array([-1,-1,1,-1,-1,1,-1,1,1,-1,1,1]),t.STATIC_DRAW);const d=t.getAttribLocation(s,"a_pos");t.enableVertexAttribArray(d),t.vertexAttribPointer(d,2,t.FLOAT,!1,0,0),t.bindVertexArray(null);const m=t.createTexture();return t.activeTexture(t.TEXTURE0),t.bindTexture(t.TEXTURE_2D,m),t.texParameteri(t.TEXTURE_2D,t.TEXTURE_MIN_FILTER,t.LINEAR),t.texParameteri(t.TEXTURE_2D,t.TEXTURE_MAG_FILTER,t.LINEAR),t.texParameteri(t.TEXTURE_2D,t.TEXTURE_WRAP_S,t.CLAMP_TO_EDGE),t.texParameteri(t.TEXTURE_2D,t.TEXTURE_WRAP_T,t.CLAMP_TO_EDGE),t.uniform1i(t.getUniformLocation(s,"u_tex"),0),{gl:t,program:s,tex:m,vao:c}}class xs{constructor(t){this.canvas=t,this.state=null}init(){return this.state=gs(this.canvas),this.state!==null}drawFrame(t){const r=this.state;if(!r)return t.close(),null;const s=t.displayWidth,a=t.displayHeight;try{return(this.canvas.width!==s||this.canvas.height!==a)&&(this.canvas.width=s,this.canvas.height=a,r.gl.viewport(0,0,s,a)),r.gl.activeTexture(r.gl.TEXTURE0),r.gl.bindTexture(r.gl.TEXTURE_2D,r.tex),r.gl.texImage2D(r.gl.TEXTURE_2D,0,r.gl.RGBA,r.gl.RGBA,r.gl.UNSIGNED_BYTE,t),r.gl.bindVertexArray(r.vao),r.gl.drawArrays(r.gl.TRIANGLES,0,6),r.gl.bindVertexArray(null),r.gl.bindTexture(r.gl.TEXTURE_2D,null),{width:s,height:a}}finally{t.close()}}dispose(){const t=this.state;t&&(t.gl.deleteTexture(t.tex),t.gl.deleteVertexArray(t.vao),t.gl.deleteProgram(t.program),this.state=null)}}function bs(e){const t=new xs(e);return t.init(),t}class ys{constructor(t=bs){this._size=null,this.canvas=document.createElement("canvas"),this.renderer=t(this.canvas),this.core=new hs(r=>this.render(r))}get surface(){return this.canvas}get size(){return this._size}onResize(t){this.resizeCb=t}onDecodedFrame(t){this.decodedCb=t,this.core.setDecodeSampler(r=>{this.lastSample=r})}decode(t){this.core.decode(t)}close(){this.core.close(),this.renderer.dispose()}render(t){var s,a;const r=this.renderer.drawFrame(t);r&&((s=this.decodedCb)==null||s.call(this,performance.now(),this.lastSample),this.lastSample=void 0,(!this._size||this._size.width!==r.width||this._size.height!==r.height)&&(this._size=r,(a=this.resizeCb)==null||a.call(this,r)))}}const vs=`#version 300 es
|
|
110
110
|
in vec2 a_pos;
|
|
111
111
|
out vec2 v_uv;
|
|
112
112
|
void main() {
|
|
@@ -127,4 +127,4 @@ void main() {
|
|
|
127
127
|
float g = Y - 0.1873 * U - 0.4681 * V;
|
|
128
128
|
float b = Y + 1.8556 * U;
|
|
129
129
|
out_color = vec4(r, g, b, 1.0);
|
|
130
|
-
}`;function Rt(e,t,r,s){const a=e.createTexture();return e.activeTexture(e.TEXTURE0+t),e.bindTexture(e.TEXTURE_2D,a),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_MIN_FILTER,e.LINEAR),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_MAG_FILTER,e.LINEAR),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_WRAP_S,e.CLAMP_TO_EDGE),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_WRAP_T,e.CLAMP_TO_EDGE),e.uniform1i(e.getUniformLocation(s,r),t),a}function Ss(e){const t=e.getContext("webgl2",{alpha:!1,antialias:!1,powerPreference:"high-performance",preserveDrawingBuffer:!0});if(!t)return null;const r=(u,y)=>{const j=t.createShader(u);return t.shaderSource(j,y),t.compileShader(j),j},s=t.createProgram(),a=r(t.VERTEX_SHADER,vs),i=r(t.FRAGMENT_SHADER,ws);t.attachShader(s,a),t.attachShader(s,i),t.linkProgram(s),t.deleteShader(a),t.deleteShader(i),t.useProgram(s);const c=t.createVertexArray();t.bindVertexArray(c);const h=t.createBuffer();t.bindBuffer(t.ARRAY_BUFFER,h),t.bufferData(t.ARRAY_BUFFER,new Float32Array([-1,-1,1,-1,-1,1,-1,1,1,-1,1,1]),t.STATIC_DRAW);const d=t.getAttribLocation(s,"a_pos");t.enableVertexAttribArray(d),t.vertexAttribPointer(d,2,t.FLOAT,!1,0,0),t.bindVertexArray(null),t.pixelStorei(t.UNPACK_ALIGNMENT,1);const m=Rt(t,0,"u_texY",s),p=Rt(t,1,"u_texU",s),g=Rt(t,2,"u_texV",s);return{gl:t,program:s,texY:m,texU:p,texV:g,vao:c}}class Rs{constructor(t){this.canvas=t,this.state=null}init(){return this.state=Ss(this.canvas),this.state!==null}drawI420(t,r,s){const a=this.state;if(!a)return null;const{gl:i}=a,c=r+1>>1,h=s+1>>1,d=r*s,m=c*h,p=t.subarray(0,d),g=t.subarray(d,d+m),u=t.subarray(d+m,d+2*m);(this.canvas.width!==r||this.canvas.height!==s)&&(this.canvas.width=r,this.canvas.height=s,i.viewport(0,0,r,s));const y=(j,L,k,A,C)=>{i.activeTexture(i.TEXTURE0+j),i.bindTexture(i.TEXTURE_2D,L),i.texImage2D(i.TEXTURE_2D,0,i.R8,k,A,0,i.RED,i.UNSIGNED_BYTE,C)};return y(0,a.texY,r,s,p),y(1,a.texU,c,h,g),y(2,a.texV,c,h,u),i.bindVertexArray(a.vao),i.drawArrays(i.TRIANGLES,0,6),i.bindVertexArray(null),{width:r,height:s}}dispose(){const t=this.state;t&&(t.gl.deleteTexture(t.texY),t.gl.deleteTexture(t.texU),t.gl.deleteTexture(t.texV),t.gl.deleteVertexArray(t.vao),t.gl.deleteProgram(t.program),this.state=null)}}const js=0;function ks(e){const t=new Rs(e);return t.init(),t}function Cs(){return new Worker(new URL("/assets/tinyh264.worker-DiJ50Hai.js",import.meta.url),{type:"module"})}class Es{constructor(t=ks,r=Cs){this.ready=!1,this.pending=[],this._size=null,this.canvas=document.createElement("canvas"),this.renderer=t(this.canvas),this.worker=r(),this.worker.onmessage=s=>this.onMessage(s.data)}get surface(){return this.canvas}get size(){return this._size}onResize(t){this.resizeCb=t}onDecodedFrame(t){this.decodedCb=t}decode(t){if(!this.ready){this.pending.push(t);return}this.post(t)}close(){this.worker.terminate(),this.renderer.dispose()}post(t){this.worker.postMessage({type:"decode",data:t,offset:0,length:t.byteLength,renderStateId:js},[t])}onMessage(t){var s,a;if(t.type==="decoderReady"){this.ready=!0;for(const i of this.pending)this.post(i);this.pending.length=0;return}const r=this.renderer.drawI420(new Uint8Array(t.data),t.width,t.height);r&&((s=this.decodedCb)==null||s.call(this,performance.now()),(!this._size||this._size.width!==r.width||this._size.height!==r.height)&&(this._size=r,(a=this.resizeCb)==null||a.call(this,r)))}}function Tt(){const e=typeof window<"u";let t=!1;try{t=!!document.createElement("canvas").getContext("webgl2")}catch{t=!1}return{secureContext:e&&window.isSecureContext===!0,webCodecs:e&&"VideoDecoder"in window,webgl2:t,wasm:typeof WebAssembly<"u"&&typeof Worker<"u"}}function Ns(e=Tt()){return e.secureContext&&e.webCodecs&&e.webgl2?new ys:e.wasm&&e.webgl2?new Es:null}function _s(e=Tt()){return e.secureContext&&e.webCodecs&&e.webgl2||e.wasm&&e.webgl2}function Ts(e=Tt()){return e.secureContext&&e.webCodecs&&e.webgl2?"high":e.wasm&&e.webgl2?"standard":"unsupported"}const Vt="tapflow.perfModeNoticeDismissed",Ps="https://www.tapflow.dev/reference/configuration#https-secure-context";function As(e,t){return e==="standard"&&!t}function Ds({open:e,onOpenChange:t}){return n.jsx(on,{open:e,onOpenChange:t,children:n.jsxs(an,{className:"sm:max-w-[440px]",children:[n.jsxs(dr,{children:[n.jsx(cn,{children:"Streaming in Standard mode"}),n.jsxs(fr,{className:"space-y-3 pt-1",children:[n.jsx("span",{className:"block",children:"This screen is running in Standard mode. For a faster, smoother picture, switch to Smooth."}),n.jsx("span",{className:"block",children:"Smooth needs the relay served over HTTPS. If you didn't set up tapflow, ask whoever did."})]})]}),n.jsxs(hr,{children:[n.jsx(ee,{variant:"outline",onClick:()=>window.open(Ps,"_blank","noopener,noreferrer"),children:"How to enable"}),n.jsx(ee,{onClick:()=>t(!1),children:"Got it"})]})]})})}const Ls={high:"Smooth",standard:"Standard",unsupported:null};function Ms(e){const{connected:t,joined:r,bootError:s,deviceReady:a,installing:i,installError:c}=e;return t?r?s?`Boot failed: ${s.length>40?s.slice(0,40)+"…":s}`:a?i?"Installing app…":c?`Install failed: ${c}`:null:"Starting device…":"Joining session…":"Connecting…"}function Pt(e){const{joined:t,fps:r,keyboardActive:s}=e,a=Ms(e),i=r>15,c=i?"#10b981":"#94a3b8",h=i?"Active":"Idle",d=o.useMemo(()=>Ts(),[]),m=Ls[d],[p,g]=o.useState(!1);o.useEffect(()=>{let y=!1;try{y=localStorage.getItem(Vt)==="1"}catch{}As(d,y)&&g(!0)},[d]);const u=y=>{if(g(y),!y)try{localStorage.setItem(Vt,"1")}catch{}};return n.jsxs("div",{className:"w-[300px] shrink-0 mt-3 rounded-xl border bg-background px-4 py-4 flex flex-col gap-3",children:[n.jsxs("div",{className:q("flex items-center",s?"text-emerald-500":"text-muted-foreground"),style:{gap:6},children:[n.jsx(Yr,{className:"h-3.5 w-3.5 shrink-0"}),n.jsx("span",{className:"text-[12px] font-medium",children:"Focus"})]}),t&&n.jsxs("div",{className:"flex items-center gap-[12px]",children:[n.jsxs("div",{className:"flex items-center gap-[4px]",children:[n.jsx("span",{className:"h-2 w-2 rounded-full shrink-0 mr-1",style:{background:c}}),n.jsx("span",{className:"text-[12px] font-mono text-foreground/75",children:r}),n.jsx("span",{className:"text-[12px] text-muted-foreground",children:"fps"}),n.jsx("span",{className:"text-[11px] text-muted-foreground/60",children:"·"}),n.jsx("span",{className:q("text-[11px]",i?"text-emerald-500":"text-muted-foreground/60"),children:h})]}),m&&n.jsxs(n.Fragment,{children:[n.jsx(tn,{orientation:"vertical",className:"h-3"}),d==="standard"?n.jsx("button",{type:"button",onClick:()=>g(!0),className:"text-[11px] text-foreground/70 hover:text-foreground underline-offset-2 hover:underline",children:m}):n.jsx("span",{className:"text-[11px] text-muted-foreground",children:m})]})]}),a&&n.jsx("p",{className:"text-[12px] text-muted-foreground leading-relaxed break-all",children:a}),n.jsx(Ds,{open:p,onOpenChange:u})]})}function gn({open:e,onOpenChange:t,sessionId:r,send:s}){const[a,i]=o.useState(""),c=o.useRef(null);o.useEffect(()=>{e?setTimeout(()=>{var d;return(d=c.current)==null?void 0:d.focus()},0):i("")},[e]);const h=()=>{a.trim()&&(s({type:"open-url",sessionId:r,payload:{url:a.trim()}}),t(!1))};return n.jsx(on,{open:e,onOpenChange:t,children:n.jsxs(an,{className:"w-[500px] max-w-[500px] h-[52px] !rounded-[18px] p-[10px] border border-border bg-background shadow-lg overflow-hidden [&>button]:hidden","aria-describedby":void 0,children:[n.jsx(cn,{className:"sr-only",children:"Open Deeplink"}),n.jsxs("div",{className:"flex items-center gap-3",children:[n.jsxs("div",{className:"flex-1 h-[32px] flex items-center gap-2 pl-[4px] pb-[1px]",children:[n.jsx(ar,{className:"h-4 w-4 text-muted-foreground shrink-0"}),n.jsx("input",{ref:c,className:"flex-1 bg-transparent text-sm outline-none placeholder:text-muted-foreground min-w-0",placeholder:"myapp://home...",value:a,onChange:d=>i(d.target.value),onKeyDown:d=>{d.key==="Enter"&&h()}})]}),n.jsx(ee,{size:"sm",disabled:!a.trim(),onClick:h,className:"shrink-0 rounded-xl h-8 px-4",children:"Open"})]})]})})}function Hs(e,t,r,s,a,i){const{x:c,y:h,width:d,height:m}=a;let p,g;if(i){const u=(e.x-t.left)/t.width;p=(1-(e.y-t.top)/t.height)*r,g=u*s}else p=(e.x-t.left)*(r/t.width),g=(e.y-t.top)*(s/t.height);return p<c||p>c+d||g<h||g>h+m?null:{x:(p-c)/d,y:(g-h)/m}}function Us(e,t,r){const s=(e.x-t.left)/t.width,a=(e.y-t.top)/t.height;return s<0||s>1||a<0||a>1?null:r?{x:a,y:1-s}:{x:s,y:a}}function xn(e){return{f0:{x:1-e.x,y:1-e.y},f1:e}}function Fs(e,t){return e>0?Math.min(1,t/e):1}const _t=22,Xt=[84,70,70,69],$s=1,Is=0,mt=1,bn=2,Bs=1,zs=2,Os=4;function Ws(e){if(e.byteLength<_t)return null;const t=new DataView(e);for(let a=0;a<Xt.length;a++)if(t.getUint8(a)!==Xt[a])return null;if(t.getUint8(4)!==$s)return null;const r=t.getUint8(5),s=r&Os?bn:r&Bs?mt:Is;return{capturedAt:Number(t.getBigUint64(6)),relayedAt:Number(t.getBigUint64(14)),codec:s,keyframe:s===mt&&(r&zs)!==0}}function yn(e){const{binaryFrameHandlerRef:t,perfHookRef:r,frameCount:s}=e,a=o.useRef(e);a.current=e,o.useEffect(()=>{let i=null,c=!1,h=!1,d;const m=()=>{if(i)return i;if(c)return null;const p=Ns();return p?(i=p,p.onResize(g=>a.current.onResize(g)),d=a.current.onDecoderReady(p),p):(c=!0,a.current.onUnsupported(),console.warn("[decoder] none available — set up HTTPS or use a supported browser"),null)};return t.current=(p,g)=>{const u=a.current.onJpegFrame;if(u&&(g==null?void 0:g.codec)!==mt){u(p,g);return}const y=m();if(y){if(!h){if(!(g!=null&&g.keyframe))return;h=!0}y.decode(p),s.current+=1}},()=>{t.current=void 0,typeof d=="function"&&d(),i==null||i.close(),i==null||i.surface.remove(),i=null}},[t,r,s])}const Ee=13,Ye=8,Yt=16,Vs=.02,Xs=100;function Ys({sessionId:e,buildId:t,send:r,connected:s,joined:a,deviceReady:i,installing:c,installed:h,installError:d,bootError:m,launching:p,setLaunching:g,chrome:u,binaryFrameHandlerRef:y,onRecordingUploaded:j,swKeyboardVisible:L,swKeyboardPending:k,onKbdToggle:A,perfHookRef:C}){const P=o.useRef(null),N=o.useRef(null),F=o.useRef(null),{fps:D,frameCount:B}=fn(),X=o.useRef(0),{recordState:$,recordCanvasRef:O,startClientRecording:Z,stopClientRecording:Re}=dn({sessionId:e,buildId:t,onRecordingUploaded:j}),fe=o.useRef(0),[ne,je]=o.useState(!1),[De,re]=o.useState(!1),[E,V]=o.useState(!1),[Y,ce]=o.useState(!1),[ke,se]=o.useState(null),[U,z]=o.useState(null),[le,Q]=o.useState(!1),[K,be]=o.useState(null),he=o.useRef(K);o.useEffect(()=>{he.current=K},[K]);const oe=o.useRef(null),ue=o.useRef(null),ae=o.useRef(!1),ie=o.useRef(!1),pe=o.useRef(0),te=o.useRef(null),me=o.useRef(null),Ce=o.useRef("idle"),_e=o.useRef(null),Ie=o.useRef(null),Le=o.useRef(null);o.useEffect(()=>{Le.current=u},[u]),o.useEffect(()=>{const l=new Image;l.onload=()=>{Ie.current=l},l.src=`data:image/png;base64,${u.framePng}`},[u.framePng]),yn({binaryFrameHandlerRef:y,perfHookRef:C,frameCount:B,onUnsupported:()=>{},onResize:l=>{const x=P.current;if(x&&(x.width!==l.width||x.height!==l.height)&&(x.width=l.width,x.height=l.height,!Le.current)){const f=O.current;f&&(f.width=l.width,f.height=l.height)}re(!0)},onDecoderReady:l=>{var b;const x=l.surface,f=P.current;x.style.position="absolute",f&&(x.style.left=f.style.left,x.style.top=f.style.top,x.style.width=f.style.width,x.style.height=f.style.height,x.style.borderRadius=f.style.borderRadius),x.style.objectFit="fill",x.style.zIndex="3",x.style.pointerEvents="none",(b=N.current)==null||b.appendChild(x);let S=null;const R=()=>{const T=P.current,M=T==null?void 0:T.getContext("2d");if(T&&M&&l.size)try{M.drawImage(l.surface,0,0,T.width,T.height)}catch{}S=requestAnimationFrame(R)};return S=requestAnimationFrame(R),()=>{S!==null&&cancelAnimationFrame(S)}},onJpegFrame:l=>{const x=performance.now();X.current&&x-X.current,X.current=x;const f=fe.current;createImageBitmap(new Blob([l],{type:"image/jpeg"})).then(S=>{if(performance.now()-x,fe.current!==f){S.close();return}const R=P.current,b=R==null?void 0:R.getContext("2d");if(!R||!b){S.close();return}if((R.width!==S.width||R.height!==S.height)&&(R.width=S.width,R.height=S.height,!Le.current)){const M=O.current;M&&(M.width=S.width,M.height=S.height)}const T=performance.now();b.drawImage(S,0,0),performance.now()-T,S.close(),re(!0),B.current+=1}).catch(()=>{})}}),o.useEffect(()=>{const l=O.current,x=N.current;l&&x&&(l.width=x.clientWidth,l.height=x.clientHeight)},[u]);const tt=o.useCallback(()=>{const l=O.current,x=P.current;if(!l||!x)return;const f=l.getContext("2d");if(!f)return;const S=Le.current;if(f.clearRect(0,0,l.width,l.height),S){Ie.current&&f.drawImage(Ie.current,0,0,l.width,l.height);const T=Math.round(S.screenCornerRadius/2*(l.height/(S.compositeHeight/2)));f.save(),f.beginPath(),T>0?f.roundRect(x.offsetLeft,x.offsetTop,x.clientWidth,x.clientHeight,T):f.rect(x.offsetLeft,x.offsetTop,x.clientWidth,x.clientHeight),f.clip(),f.drawImage(x,x.offsetLeft,x.offsetTop,x.clientWidth,x.clientHeight),f.restore()}else f.drawImage(x,0,0,l.width,l.height);const R=he.current;if(R)for(const T of[R.f0,R.f1]){const M=S?x.offsetLeft+T.x*x.clientWidth:T.x*l.width,W=S?x.offsetTop+T.y*x.clientHeight:T.y*l.height;ae.current?(f.beginPath(),f.arc(M,W,Ye,0,Math.PI*2),f.fillStyle="rgba(255,255,255,0.92)",f.fill(),f.strokeStyle="rgba(0,0,0,0.2)",f.lineWidth=1,f.stroke()):(f.beginPath(),f.arc(M,W,Ee,0,Math.PI*2),f.strokeStyle="rgba(0,0,0,0.3)",f.lineWidth=3,f.stroke(),f.beginPath(),f.arc(M,W,Ee,0,Math.PI*2),f.strokeStyle="rgba(255,255,255,0.65)",f.lineWidth=1.5,f.stroke())}const b=me.current;if(b){const T=Ce.current,M=_e.current;if(f.save(),T==="down")f.beginPath(),f.arc(b.x,b.y,Ye,0,Math.PI*2),f.fillStyle="rgba(255,255,255,0.92)",f.fill(),f.strokeStyle="rgba(0,0,0,0.2)",f.lineWidth=1,f.stroke();else if(T==="release"&&M){const W=Math.min((performance.now()-M.startTime)/350,1);f.beginPath(),f.arc(b.x,b.y,Ye+26*W,0,Math.PI*2),f.strokeStyle=`rgba(255,255,255,${(1-W)*.55})`,f.lineWidth=1.5,f.stroke(),W>=1&&(Ce.current="idle",_e.current=null)}else f.beginPath(),f.arc(b.x,b.y,Ee,0,Math.PI*2),f.strokeStyle="rgba(0,0,0,0.3)",f.lineWidth=3,f.stroke(),f.beginPath(),f.arc(b.x,b.y,Ee,0,Math.PI*2),f.strokeStyle="rgba(255,255,255,0.65)",f.lineWidth=1.5,f.stroke();f.restore()}},[]),Be=o.useCallback(()=>{const l=P.current;if(!l)return;const x=document.createElement("canvas"),f=x.getContext("2d");f&&(x.width=l.width,x.height=l.height,f.drawImage(l,0,0),x.toBlob(S=>{if(!S)return;const R=URL.createObjectURL(S),b=document.createElement("a");b.href=R,b.download=`tapflow-${Date.now()}.png`,b.click(),URL.revokeObjectURL(R)},"image/png"))},[]),ye=o.useCallback(()=>{if($==="idle"){const l=O.current;if(!l)return;const x=N.current;if(x&&x.clientWidth>0)l.width=x.clientWidth,l.height=x.clientHeight;else{const f=P.current;if(f&&f.width>0)l.width=f.width,l.height=f.height;else return}Z(tt)}else $==="recording"&&Re()},[$,Z,Re,tt]),Te=o.useCallback(()=>{r({type:"input:rotate",sessionId:e}),V(l=>!l)},[r,e]),it=o.useRef(E);o.useEffect(()=>{it.current=E},[E]),o.useEffect(()=>()=>{it.current&&r({type:"input:rotate",sessionId:e})},[]),o.useEffect(()=>{const l=new Set(["ShiftLeft","ShiftRight","ControlLeft","ControlRight","MetaLeft","MetaRight"]),x=b=>{if(b.code==="AltLeft"||b.code==="AltRight"){ie.current=!0;return}if(b.metaKey){const M=document.activeElement;if(!M||M.tagName!=="INPUT"&&M.tagName!=="TEXTAREA"){if(!b.shiftKey&&b.code==="KeyK"){b.preventDefault(),je(!0);return}if(!b.shiftKey&&b.code==="KeyS"){b.preventDefault(),Be();return}if(b.shiftKey&&b.code==="KeyY"){b.preventDefault(),ye();return}if(b.shiftKey&&b.code==="KeyO"){b.preventDefault(),Te();return}if(b.shiftKey&&b.code==="KeyU"){b.preventDefault(),r({type:"input:button",sessionId:e,payload:{name:"home"}});return}if(b.shiftKey&&b.code==="KeyK"){b.preventDefault(),k||A();return}}}if(!Y||l.has(b.code))return;b.preventDefault();const T=(b.shiftKey?2:0)|(b.ctrlKey?1:0)|(b.metaKey?8:0);r({type:"input:key",sessionId:e,payload:{code:b.code,modifiers:T}})},f=()=>{ae.current&&(ae.current=!1,Q(!1),r({type:"input:pinch:end",sessionId:e})),ie.current=!1,be(null)},S=b=>{(b.code==="AltLeft"||b.code==="AltRight")&&f()},R=()=>{ie.current&&f()};return window.addEventListener("keydown",x),window.addEventListener("keyup",S),window.addEventListener("blur",R),()=>{window.removeEventListener("keydown",x),window.removeEventListener("keyup",S),window.removeEventListener("blur",R)}},[Y,r,e,Be,ye,Te,A,k]),o.useEffect(()=>{if(!Y)return;const l=x=>{const f=N.current??P.current;f&&!f.contains(x.target)&&ce(!1)};return document.addEventListener("pointerdown",l),()=>document.removeEventListener("pointerdown",l)},[Y]);const Pe=o.useCallback(l=>{const x=(E?F.current:null)??N.current;if(!x)return null;const f=x.getBoundingClientRect(),S=u.compositeWidth/2,R=u.compositeHeight/2,b=u.screenRect.x/2,T=u.screenRect.y/2,M=u.screenRect.width/2,W=u.screenRect.height/2;return Hs({x:l.clientX,y:l.clientY},f,S,R,{x:b,y:T,width:M,height:W},E)},[u,E]),ze=o.useCallback(l=>{const x=Pe(l);return x?xn(x):null},[Pe]),Je=o.useCallback(l=>{const x=E?F.current:N.current;if(!x)return null;const f=x.getBoundingClientRect();let S,R;if(E){const T=f.height-(l.clientY-f.top),M=l.clientX-f.left;S=T*(u.compositeWidth/f.height),R=M*(u.compositeHeight/f.width)}else S=(l.clientX-f.left)*(u.compositeWidth/f.width),R=(l.clientY-f.top)*(u.compositeHeight/f.height);const b=u.screenRect;if(S>=b.x&&S<=b.x+b.width&&R>=b.y&&R<=b.y+b.height)return null;for(const T of u.buttons){const M=S-T.normalOffset.x,W=R-T.normalOffset.y;if(M*M+W*W<Xs**2)return T.name}return null},[u,E]),Oe=o.useCallback(l=>{const x=P.current,f=O.current;return x&&x.clientWidth>0?{x:x.offsetLeft+l.x*x.clientWidth,y:x.offsetTop+l.y*x.clientHeight}:{x:l.x*((f==null?void 0:f.width)??1),y:l.y*((f==null?void 0:f.height)??1)}},[]),ge=o.useCallback(l=>{if(ce(!0),ie.current){const b=ze(l);if(!b)return;ae.current=!0,Q(!0),l.target.setPointerCapture(l.pointerId),be(b),r({type:"input:pinch:start",sessionId:e,payload:b});return}const x=Je(l);if(x){oe.current=x,se(x),l.target.setPointerCapture(l.pointerId),r({type:"input:button",sessionId:e,payload:{name:x,phase:"down"}});return}const f=Pe(l);if(!f)return;ue.current=f,l.target.setPointerCapture(l.pointerId),me.current=Oe(f),Ce.current="down",_e.current=null;const S=l.currentTarget.getBoundingClientRect(),R=te.current;R&&(R.style.display="block",R.style.left=`${l.clientX-S.left}px`,R.style.top=`${l.clientY-S.top}px`,R.style.width=`${Ye*2}px`,R.style.height=`${Ye*2}px`,R.style.background="rgba(255,255,255,0.92)",R.style.border="1.5px solid rgba(0,0,0,0.2)",R.style.boxShadow="0 0 0 1px rgba(0,0,0,0.15), 0 0 8px rgba(255,255,255,0.25)"),r({type:"input:touch:start",sessionId:e,payload:f})},[Je,Pe,ze,Oe,r,e]),ct=o.useCallback(l=>{if(l.buttons===0){if(z(Je(l)),ie.current){be(ze(l)),me.current=null;const T=te.current;T&&(T.style.display="none")}else{be(null);const T=Pe(l);me.current=T?Oe(T):null,Ce.current!=="down"&&(Ce.current="idle");const M=te.current;if(M)if(T){const W=l.currentTarget.getBoundingClientRect();M.style.display="block",M.style.left=`${l.clientX-W.left}px`,M.style.top=`${l.clientY-W.top}px`,M.style.width=`${Ee*2}px`,M.style.height=`${Ee*2}px`,M.style.background="transparent",M.style.border="1.5px solid rgba(255,255,255,0.6)",M.style.boxShadow="0 0 0 1px rgba(0,0,0,0.3)"}else M.style.display="none"}return}if(ae.current){const T=ze(l);if(!T)return;const M=performance.now();if(M-pe.current<Yt)return;pe.current=M,be(T),r({type:"input:pinch:move",sessionId:e,payload:T});return}if(oe.current||!ue.current)return;const x=Pe(l);if(!x)return;const f=x.x-ue.current.x,S=x.y-ue.current.y;if(Math.sqrt(f*f+S*S)<Vs)return;const R=performance.now();if(R-pe.current<Yt)return;pe.current=R,me.current=Oe(x);const b=te.current;if(b&&b.style.display!=="none"){const T=l.currentTarget.getBoundingClientRect();b.style.left=`${l.clientX-T.left}px`,b.style.top=`${l.clientY-T.top}px`}r({type:"input:touch:move",sessionId:e,payload:x})},[Je,Pe,ze,Oe,r,e]),Me=o.useCallback(()=>{if(ae.current){ae.current=!1,Q(!1),be(null),r({type:"input:pinch:end",sessionId:e});return}if(ue.current=null,oe.current){r({type:"input:button",sessionId:e,payload:{name:oe.current,phase:"up"}}),oe.current=null,setTimeout(()=>se(null),100);return}Ce.current="release",_e.current={startTime:performance.now()};const l=te.current;l&&(l.style.width=`${Ee*2}px`,l.style.height=`${Ee*2}px`,l.style.background="transparent",l.style.border="1.5px solid rgba(255,255,255,0.6)",l.style.boxShadow="0 0 0 1px rgba(0,0,0,0.3)"),r({type:"input:touch:end",sessionId:e})},[r,e]),We=o.useCallback(()=>{if(ae.current){ae.current=!1,Q(!1),be(null),r({type:"input:pinch:end",sessionId:e});return}if(ue.current=null,oe.current){r({type:"input:button",sessionId:e,payload:{name:oe.current,phase:"up"}}),oe.current=null,se(null);return}Ce.current="release",_e.current={startTime:performance.now()},r({type:"input:touch:end",sessionId:e})},[r,e]),St=o.useCallback(()=>{z(null),be(null),me.current=null;const l=te.current;l&&(l.style.display="none")},[]),He=u.compositeWidth/2,lt=u.compositeHeight/2,Ze=Fs(lt,750),Ve=Math.round(He*Ze),Xe=Math.round(lt*Ze),Qe=u.screenRect.x/u.compositeWidth*100,v=u.screenRect.y/u.compositeHeight*100,_=u.screenRect.width/u.compositeWidth*100,I=u.screenRect.height/u.compositeHeight*100,w=Math.round(u.screenCornerRadius/2*Ze),G=n.jsxs(n.Fragment,{children:[n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:()=>r({type:"input:button",sessionId:e,payload:{name:"home"}}),children:n.jsx(ln,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsxs("span",{className:"flex items-center gap-3",children:["Home ",n.jsxs(Et,{children:[n.jsx(Ge,{children:"⌘"}),n.jsx(Ge,{children:"⇧"}),n.jsx(Ge,{children:"U"})]})]})})]}),n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",disabled:k,onClick:A,"data-active":L,children:k?n.jsx(pt,{className:"h-4 w-4 animate-spin"}):n.jsx(Ur,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsxs("span",{className:"flex items-center gap-3",children:["Software keyboard ",n.jsxs(Et,{children:[n.jsx(Ge,{children:"⌘"}),n.jsx(Ge,{children:"⇧"}),n.jsx(Ge,{children:"K"})]})]})})]})]}),H=h&&t?n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",disabled:p,onClick:()=>{g(!0),r({type:"app:launch",sessionId:e,buildId:t})},children:p?n.jsx(pt,{className:"h-4 w-4 animate-spin"}):n.jsx(rn,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:p?"Launching…":"Launch app"})]}):null;return n.jsxs("div",{className:"flex items-start justify-center gap-16",children:[n.jsx("canvas",{ref:O,style:{display:"none"}}),n.jsx(gn,{open:ne,onOpenChange:je,sessionId:e,send:r}),n.jsx(hn,{joined:a,onDeepLink:()=>je(!0),onScreenshot:Be,onRecordToggle:ye,recordState:$,onRotate:Te,platformSlot:G,launchSlot:H}),n.jsxs("div",{className:"flex items-start gap-8",children:[n.jsxs("div",{ref:F,style:{width:E?Xe:Ve,height:E?Ve:Xe,position:"relative",flexShrink:0},children:[n.jsxs("div",{ref:N,className:`relative ${U?"cursor-pointer":"cursor-default"}`,style:{width:Ve,height:Xe,...E?{position:"absolute",top:(Ve-Xe)/2,left:(Xe-Ve)/2,transform:"rotate(-90deg)",transformOrigin:"center center"}:{}},onPointerDown:ge,onPointerMove:ct,onPointerUp:Me,onPointerCancel:We,onPointerLeave:St,children:[n.jsx("img",{src:`data:image/png;base64,${u.framePng}`,style:{position:"absolute",top:0,left:0,zIndex:2,width:"100%",height:"100%",display:"block",pointerEvents:"none",userSelect:"none"},draggable:!1,alt:""}),n.jsx("canvas",{ref:P,style:{position:"absolute",zIndex:3,left:`${Qe}%`,top:`${v}%`,width:`${_}%`,height:`${I}%`,borderRadius:w>0?`${w}px`:void 0,backgroundColor:"#010101",cursor:"none",visibility:De?"visible":"hidden"}}),!De&&n.jsx("div",{className:"absolute animate-pulse bg-zinc-700",style:{zIndex:3,left:`${Qe}%`,top:`${v}%`,width:`${_}%`,height:`${I}%`,borderRadius:w>0?`${w}px`:void 0}}),K&&(()=>{const l=Qe/100,x=v/100,f=_/100,S=I/100,R=(b,T)=>({left:`${(l+b*f)*100}%`,top:`${(x+T*S)*100}%`});return n.jsx(n.Fragment,{children:[K.f0,K.f1].map((b,T)=>n.jsx("div",{style:{position:"absolute",zIndex:10,borderRadius:"50%",transform:"translate(-50%, -50%)",pointerEvents:"none",transition:"width 0.1s ease, height 0.1s ease, background 0.1s ease",...le?{width:Ye*2,height:Ye*2,background:"rgba(255,255,255,0.92)",border:"1.5px solid rgba(0,0,0,0.2)",boxShadow:"0 0 0 1px rgba(0,0,0,0.15), 0 0 8px rgba(255,255,255,0.25)"}:{width:Ee*2,height:Ee*2,background:"transparent",border:"1.5px solid rgba(255,255,255,0.6)",boxShadow:"0 0 0 1px rgba(0,0,0,0.3)"},...R(b.x,b.y)}},T))})})(),a&&D===0&&n.jsx("div",{style:{position:"absolute",zIndex:8,left:`${Qe}%`,top:`${v}%`,width:`${_}%`,height:`${I}%`,display:"flex",alignItems:"center",justifyContent:"center",pointerEvents:"none"},children:n.jsx("span",{style:{color:"white",fontSize:"0.875rem"},children:"Waiting for first frame..."})}),u.buttons.map(l=>{const x=ke===l.name,f=U===l.name,S=l.anchor==="bottom",R=l.anchor==="top",b=S?(l.normalOffset.y-l.buttonH/2)/u.compositeHeight*100:R?l.rolloverOffset.y/u.compositeHeight*100:(l.normalOffset.y-l.buttonH/2)/u.compositeHeight*100,T=l.buttonH/u.compositeHeight*100,M=l.buttonW/u.compositeWidth*100,W=l.buttonW/2,de=(l.rolloverOffset.x-W)/u.compositeWidth*100,Ae=(2*l.rolloverOffset.x-l.normalOffset.x-W)/u.compositeWidth*100,ut=l.rolloverOffset.x/u.compositeWidth*100,nt=S?(l.normalOffset.y-l.buttonH/2)/u.compositeHeight*100:R?l.rolloverOffset.y/u.compositeHeight*100:(l.normalOffset.y-l.buttonH/2)/u.compositeHeight*100,$t=R?(2*l.rolloverOffset.y-l.normalOffset.y)/u.compositeHeight*100:0,Yn=l.onTop?4:1;return n.jsxs(o.Fragment,{children:[l.buttonPng&&n.jsx("img",{src:`data:image/png;base64,${l.buttonPng}`,style:{position:"absolute",zIndex:Yn,top:`${R&&f?$t:b}%`,left:`${R?de:f?Ae:de}%`,width:`${M}%`,height:`${T}%`,transition:R?"top 0.15s ease":"left 0.15s ease",pointerEvents:"none",userSelect:"none"},draggable:!1,alt:""}),x&&l.pressedPng&&l.pressedRect&&n.jsx("img",{src:`data:image/png;base64,${l.pressedPng}`,style:{position:"absolute",zIndex:l.onTop?3:1,left:`${R?de:f?Ae:de}%`,top:`${R&&f?$t:b}%`,width:`${l.pressedRect.width/u.compositeWidth*100}%`,height:`${l.pressedRect.height/u.compositeHeight*100}%`,pointerEvents:"none",userSelect:"none"},draggable:!1,alt:""}),f&&n.jsx("div",{className:"bg-foreground/85 text-background text-[11px] px-[7px] py-1.5 rounded-lg whitespace-nowrap pointer-events-none",style:{position:"absolute",zIndex:5,left:`${ut}%`,top:`${nt}%`,transform:"translate(-50%, calc(-100% - 8px))"},children:l.accessibilityTitle})]},l.name)})]}),n.jsx("div",{ref:te,style:{display:"none",position:"absolute",zIndex:20,borderRadius:"50%",transform:"translate(-50%, -50%)",pointerEvents:"none",transition:"width 0.1s ease, height 0.1s ease, background 0.1s ease, box-shadow 0.1s ease"}})]}),n.jsx(Pt,{joined:a,fps:D,connected:s,deviceReady:i,bootError:m,installing:c,installError:d,keyboardActive:Y})]})]})}const Ke=13,st=8,Kt=16,Ks=.02,jt=720;function Gs({sessionId:e,buildId:t,send:r,connected:s,joined:a,deviceReady:i,installing:c,installed:h,installError:d,bootError:m,launching:p,setLaunching:g,androidButtons:u,binaryFrameHandlerRef:y,onRecordingUploaded:j,screenWidth:L,screenHeight:k,cornerRadius:A,perfHookRef:C}){const P=o.useRef(null),N=o.useRef(null),F=o.useRef(null),{fps:D,frameCount:B}=fn(),{recordState:X,recordCanvasRef:$,startClientRecording:O,stopClientRecording:Z}=dn({sessionId:e,buildId:t,onRecordingUploaded:j}),[Re,fe]=o.useState(!1),[ne,je]=o.useState(!1),[De,re]=o.useState(!1),E=o.useRef(null),[V,Y]=o.useState(null),[ce,ke]=o.useState(!1),[se,U]=o.useState(!1),[z,le]=o.useState(!1),[Q,K]=o.useState(null),be=o.useRef(Q);o.useEffect(()=>{be.current=Q},[Q]);const he=o.useRef(!1),oe=o.useRef(!1),ue=o.useRef(null),ae=o.useRef(0),ie=o.useRef(null),pe=o.useRef(null),te=o.useRef("idle"),me=o.useRef(null);yn({binaryFrameHandlerRef:y,perfHookRef:C,frameCount:B,onUnsupported:()=>re(!0),onResize:v=>{je(!0);const _=E.current;(!_||_.width!==v.width||_.height!==v.height)&&(E.current=v,Y(v))},onDecoderReady:v=>{var I;F.current=v;const _=v.surface;_.style.display="block",_.style.width="100%",_.style.height="100%",_.style.objectFit="fill",(I=P.current)==null||I.appendChild(_)}});const Ce=o.useCallback(()=>{var M;const v=$.current,_=(M=F.current)==null?void 0:M.surface,I=E.current;if(!v||!_||!I)return;const w=v.getContext("2d");if(!w)return;const G=I.width,H=I.height,l=v.width>v.height!=G>H;w.save(),l&&(w.translate(v.width,0),w.rotate(Math.PI/2)),w.drawImage(_,0,0,G,H);const x=Math.max(G,H),f=x>jt?x/jt:1,S=Ke*f,R=st*f,b=be.current;if(b)for(const W of[b.f0,b.f1]){const de=W.x*G,Ae=W.y*H;he.current?(w.beginPath(),w.arc(de,Ae,R,0,Math.PI*2),w.fillStyle="rgba(255,255,255,0.92)",w.fill(),w.strokeStyle="rgba(0,0,0,0.2)",w.lineWidth=f,w.stroke()):(w.beginPath(),w.arc(de,Ae,S,0,Math.PI*2),w.strokeStyle="rgba(0,0,0,0.3)",w.lineWidth=3*f,w.stroke(),w.beginPath(),w.arc(de,Ae,S,0,Math.PI*2),w.strokeStyle="rgba(255,255,255,0.65)",w.lineWidth=1.5*f,w.stroke())}const T=pe.current;if(T){const W=T.x*G,de=T.y*H,Ae=te.current,ut=me.current;if(Ae==="down")w.beginPath(),w.arc(W,de,R,0,Math.PI*2),w.fillStyle="rgba(255,255,255,0.92)",w.fill(),w.strokeStyle="rgba(0,0,0,0.2)",w.lineWidth=f,w.stroke();else if(Ae==="release"&&ut){const nt=Math.min((performance.now()-ut.startTime)/350,1);w.beginPath(),w.arc(W,de,R+26*f*nt,0,Math.PI*2),w.strokeStyle=`rgba(255,255,255,${(1-nt)*.55})`,w.lineWidth=1.5*f,w.stroke(),nt>=1&&(te.current="idle",me.current=null)}else w.beginPath(),w.arc(W,de,S,0,Math.PI*2),w.strokeStyle="rgba(0,0,0,0.3)",w.lineWidth=3*f,w.stroke(),w.beginPath(),w.arc(W,de,S,0,Math.PI*2),w.strokeStyle="rgba(255,255,255,0.65)",w.lineWidth=1.5*f,w.stroke()}w.restore()},[]),_e=o.useCallback(()=>{var G;const v=(G=F.current)==null?void 0:G.surface,_=E.current;if(!v||!_)return;const I=document.createElement("canvas"),w=I.getContext("2d");w&&(I.width=_.width,I.height=_.height,w.drawImage(v,0,0,_.width,_.height),I.toBlob(H=>{if(!H)return;const l=URL.createObjectURL(H),x=document.createElement("a");x.href=l,x.download=`tapflow-${Date.now()}.png`,x.click(),URL.revokeObjectURL(l)},"image/png"))},[]),Ie=o.useCallback(()=>{if(X==="idle"){const v=$.current;if(!v)return;const _=E.current;if(!_)return;const I=Be.current;v.width=I?_.height:_.width,v.height=I?_.width:_.height,O(Ce)}else X==="recording"&&Z()},[X,O,Z,Ce]),Le=o.useCallback(()=>{r({type:"input:rotate",sessionId:e}),ke(v=>!v)},[r,e]),tt=o.useRef(ce);o.useEffect(()=>{tt.current=ce},[ce]),o.useEffect(()=>()=>{tt.current&&r({type:"input:rotate",sessionId:e})},[]),o.useEffect(()=>{const v=new Set(["ShiftLeft","ShiftRight","ControlLeft","ControlRight","MetaLeft","MetaRight"]),_=H=>{if(H.code==="AltLeft"||H.code==="AltRight"){oe.current=!0;return}if(H.metaKey){const x=document.activeElement;if(!x||x.tagName!=="INPUT"&&x.tagName!=="TEXTAREA"){if(!H.shiftKey&&H.code==="KeyK"){H.preventDefault(),fe(!0);return}if(!H.shiftKey&&H.code==="KeyS"){H.preventDefault(),_e();return}if(H.shiftKey&&H.code==="KeyY"){H.preventDefault(),Ie();return}if(H.shiftKey&&H.code==="KeyO"){H.preventDefault(),Le();return}}}if(!se||v.has(H.code))return;H.preventDefault();const l=(H.shiftKey?2:0)|(H.ctrlKey?1:0)|(H.metaKey?8:0);r({type:"input:key",sessionId:e,payload:{code:H.code,modifiers:l}})},I=()=>{he.current&&(he.current=!1,le(!1),r({type:"input:pinch:end",sessionId:e})),oe.current=!1,K(null)},w=H=>{(H.code==="AltLeft"||H.code==="AltRight")&&I()},G=()=>{oe.current&&I()};return window.addEventListener("keydown",_),window.addEventListener("keyup",w),window.addEventListener("blur",G),()=>{window.removeEventListener("keydown",_),window.removeEventListener("keyup",w),window.removeEventListener("blur",G)}},[se,r,e,_e,Ie,Le]),o.useEffect(()=>{if(!se)return;const v=_=>{const I=N.current??P.current;I&&!I.contains(_.target)&&U(!1)};return document.addEventListener("pointerdown",v),()=>document.removeEventListener("pointerdown",v)},[se]);const Be=o.useRef(!1),ye=o.useCallback(v=>{const _=P.current;if(!_)return null;const I=_.getBoundingClientRect();return Us({x:v.clientX,y:v.clientY},I,Be.current)},[]),Te=o.useCallback(v=>{const _=ye(v);return _?xn(_):null},[ye]),it=o.useCallback(v=>{if(oe.current){const G=Te(v);if(!G)return;he.current=!0,le(!0),v.target.setPointerCapture(v.pointerId);const H=ie.current;H&&(H.style.display="none"),K(G),r({type:"input:pinch:start",sessionId:e,payload:G});return}const _=ye(v);if(!_)return;U(!0),ue.current=_,v.target.setPointerCapture(v.pointerId);const I=v.currentTarget.getBoundingClientRect();pe.current=_,te.current="down",me.current=null;const w=ie.current;w&&(w.style.display="block",w.style.left=`${v.clientX-I.left}px`,w.style.top=`${v.clientY-I.top}px`,w.style.width=`${st*2}px`,w.style.height=`${st*2}px`,w.style.background="rgba(255,255,255,0.92)",w.style.border="1.5px solid rgba(0,0,0,0.2)",w.style.boxShadow="0 0 0 1px rgba(0,0,0,0.15), 0 0 8px rgba(255,255,255,0.25)"),r({type:"input:touch:start",sessionId:e,payload:_})},[ye,Te,r,e]),Pe=o.useCallback(v=>{if(v.buttons===0){if(oe.current){K(Te(v)),pe.current=null;const R=ie.current;R&&(R.style.display="none");return}const x=ye(v),f=v.currentTarget.getBoundingClientRect(),S=ie.current;x?(pe.current=x,te.current!=="down"&&(te.current="idle"),S&&(S.style.display="block",S.style.left=`${v.clientX-f.left}px`,S.style.top=`${v.clientY-f.top}px`,S.style.width=`${Ke*2}px`,S.style.height=`${Ke*2}px`,S.style.background="transparent",S.style.border="1.5px solid rgba(255,255,255,0.6)",S.style.boxShadow="0 0 0 1px rgba(0,0,0,0.3)")):(pe.current=null,S&&(S.style.display="none"));return}if(he.current){const x=Te(v);if(!x)return;const f=performance.now();if(f-ae.current<Kt)return;ae.current=f,K(x),r({type:"input:pinch:move",sessionId:e,payload:x});return}if(!ue.current)return;const _=ye(v);if(!_)return;const I=_.x-ue.current.x,w=_.y-ue.current.y;if(Math.sqrt(I*I+w*w)<Ks)return;const G=performance.now();if(G-ae.current<Kt)return;ae.current=G;const H=v.currentTarget.getBoundingClientRect();pe.current=_;const l=ie.current;l&&l.style.display!=="none"&&(l.style.left=`${v.clientX-H.left}px`,l.style.top=`${v.clientY-H.top}px`),r({type:"input:touch:move",sessionId:e,payload:_})},[ye,Te,r,e]),ze=o.useCallback(()=>{if(he.current){he.current=!1,le(!1),K(null),r({type:"input:pinch:end",sessionId:e});return}ue.current=null,te.current="release",me.current={startTime:performance.now()};const v=ie.current;v&&(v.style.width=`${Ke*2}px`,v.style.height=`${Ke*2}px`,v.style.background="transparent",v.style.border="1.5px solid rgba(255,255,255,0.6)",v.style.boxShadow="0 0 0 1px rgba(0,0,0,0.3)"),r({type:"input:touch:end",sessionId:e})},[r,e]),Je=o.useCallback(()=>{if(he.current){he.current=!1,le(!1),K(null),r({type:"input:pinch:end",sessionId:e});return}ue.current=null,te.current="release",me.current={startTime:performance.now()},r({type:"input:touch:end",sessionId:e})},[r,e]),Oe=o.useCallback(()=>{K(null),pe.current=null;const v=ie.current;v&&(v.style.display="none")},[]),ge=V??(L&&k?{width:L,height:k}:null),ct=ge?Math.min(1,jt/Math.max(ge.width,ge.height)):.3,Me=ge?Math.round(ge.width*ct):324,We=ge?Math.round(ge.height*ct):720,St=ge?ge.width>ge.height:!1,He=ce&&!St;o.useLayoutEffect(()=>{Be.current=He},[He]);const lt=He?We:Me,Ft=He?Me:We,Ze=A!=null?Math.round(A*Me):22,Ve=He?{position:"absolute",width:Me,height:We,top:(Me-We)/2,left:(We-Me)/2,transform:"rotate(90deg)",transformOrigin:"center center",visibility:ne?"visible":"hidden",cursor:"none"}:{visibility:ne?"visible":"hidden",cursor:"none"},Xe=n.jsx(n.Fragment,{children:u==null?void 0:u.map(v=>n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:()=>r({type:"input:button",sessionId:e,payload:{name:v.name}}),children:v.name==="back"?n.jsx(Sr,{className:"h-4 w-4"}):v.name==="recent_apps"?n.jsx(Kn,{className:"h-4 w-4"}):v.name==="volume_up"?n.jsx(Qr,{className:"h-4 w-4"}):v.name==="volume_down"?n.jsx(ts,{className:"h-4 w-4"}):v.name==="power"?n.jsx(Or,{className:"h-4 w-4"}):n.jsx(ln,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:v.accessibilityTitle})]},v.name))}),Qe=h&&t?n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",disabled:p||c,onClick:()=>{g(!0),r({type:"app:launch",sessionId:e,buildId:t})},children:p?n.jsx(pt,{className:"h-4 w-4 animate-spin"}):n.jsx(rn,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:p?"Launching…":c?"Installing…":"Launch app"})]}):null;return n.jsxs("div",{className:"flex items-start justify-center gap-16",children:[n.jsx("canvas",{ref:$,style:{display:"none"}}),n.jsx(gn,{open:Re,onOpenChange:fe,sessionId:e,send:r}),n.jsx(hn,{joined:a,onDeepLink:()=>fe(!0),onScreenshot:_e,onRecordToggle:Ie,recordState:X,onRotate:Le,platformSlot:Xe,launchSlot:Qe}),n.jsxs("div",{className:"flex items-start gap-8",children:[n.jsx("div",{style:{background:"#1c1c1e",borderRadius:`${Ze+12}px`,padding:"12px",flexShrink:0,boxShadow:"0 8px 32px rgba(0,0,0,0.45), inset 0 1px 0 rgba(255,255,255,0.06)"},children:n.jsx("div",{ref:N,className:"relative",style:{width:lt,height:Ft,backgroundColor:"#010101",borderRadius:`${Ze}px`,overflow:"hidden"},children:De?n.jsx("div",{className:"absolute inset-0 flex items-center justify-center p-4 text-center",children:n.jsxs("span",{style:{color:"rgba(255,255,255,0.6)",fontSize:"0.875rem"},children:["이 환경에서는 스트리밍을 표시할 수 없습니다.",n.jsx("br",{}),"Chrome/Edge 또는 HTTPS 환경에서 다시 시도해 주세요."]})}):n.jsxs(n.Fragment,{children:[n.jsx("div",{ref:P,className:He?void 0:"block w-full h-full",style:Ve,onPointerDown:it,onPointerMove:Pe,onPointerUp:ze,onPointerCancel:Je,onPointerLeave:Oe}),!ne&&n.jsx("div",{className:"absolute inset-0 animate-pulse bg-zinc-700"}),!ne&&i&&n.jsx("div",{className:"absolute inset-0 flex items-center justify-center pointer-events-none",children:n.jsx("span",{style:{color:"rgba(255,255,255,0.6)",fontSize:"0.875rem"},children:"Waiting for stream…"})}),n.jsx("div",{ref:ie,style:{display:"none",position:"absolute",zIndex:20,borderRadius:"50%",transform:"translate(-50%, -50%)",pointerEvents:"none",transition:"width 0.1s ease, height 0.1s ease, background 0.1s ease, box-shadow 0.1s ease"}}),Q&&n.jsx(n.Fragment,{children:[Q.f0,Q.f1].map((v,_)=>n.jsx("div",{style:{position:"absolute",zIndex:10,borderRadius:"50%",transform:"translate(-50%, -50%)",pointerEvents:"none",transition:"width 0.1s ease, height 0.1s ease, background 0.1s ease",left:`${v.x*100}%`,top:`${v.y*100}%`,...z?{width:st*2,height:st*2,background:"rgba(255,255,255,0.92)",border:"1.5px solid rgba(0,0,0,0.2)",boxShadow:"0 0 0 1px rgba(0,0,0,0.15), 0 0 8px rgba(255,255,255,0.25)"}:{width:Ke*2,height:Ke*2,background:"transparent",border:"1.5px solid rgba(255,255,255,0.6)",boxShadow:"0 0 0 1px rgba(0,0,0,0.3)"}}},_))})]})})}),n.jsx(Pt,{joined:a,fps:D,connected:s,deviceReady:i,bootError:m,installing:c,installError:d,keyboardActive:se})]})]})}function qs(e,t){const r=new DataView(e),s=Math.floor(e.byteLength/2),a=Math.floor(s/t),i=[];for(let c=0;c<t;c++)i.push(new Float32Array(a));for(let c=0;c<a;c++)for(let h=0;h<t;h++){const d=r.getInt16((c*t+h)*2,!0);i[h][c]=d/32768}return i}const Js=44100,kt=2,Gt=.06,Zs=.3;function Qs(){const e=o.useRef(null),t=o.useRef(0),r=o.useCallback(()=>{if(e.current)return e.current;const a=window.AudioContext??window.webkitAudioContext;return a?(e.current=new a,e.current):null},[]),s=o.useCallback(a=>{var u;const i=r();if(!i)return;i.state==="suspended"&&i.resume();const c=qs(a,kt),h=((u=c[0])==null?void 0:u.length)??0;if(h===0)return;const d=i.createBuffer(kt,h,Js);for(let y=0;y<kt;y++)d.getChannelData(y).set(c[y]);const m=i.createBufferSource();m.buffer=d,m.connect(i.destination);const p=i.currentTime;let g=t.current;(g<p+.005||g>p+Zs+Gt)&&(g=p+Gt),m.start(g),t.current=g+d.duration},[r]);return o.useEffect(()=>()=>{var a;(a=e.current)==null||a.close(),e.current=null},[]),{pushFrame:s}}function eo({sessionId:e,deviceId:t,buildId:r,resetMode:s,onRecordingUploaded:a}){const i=o.useRef(()=>{});os();const c=o.useRef(null),h=o.useRef(null),d=o.useRef([]);o.useRef({onFrameBegin:()=>{var U;return(U=c.current)==null?void 0:U.onFrameBegin()},onFrameEnd:U=>{var Q,K;const z=d.current.shift()??null,le=z?{...U,capturedAt:z.capturedAt,relayedAt:z.relayedAt}:U;(Q=c.current)==null||Q.onFrameEnd(le),(K=h.current)==null||K.call(h,le)}});const[m,p]=o.useState(!1),[g,u]=o.useState(!1),[y,j]=o.useState(null),[L,k]=o.useState(!1),[A,C]=o.useState(!1),[P,N]=o.useState(null),[F,D]=o.useState(null),[B,X]=o.useState(!1),[$,O]=o.useState(!1),[Z,Re]=o.useState(!1),fe=o.useRef(void 0),{pushFrame:ne}=Qs(),je=o.useCallback(U=>{if(U.type==="session:joined"&&(p(!0),i.current({type:"device:boot",sessionId:e,payload:{deviceId:t,resetMode:s,acceptH264:_s(),secureContext:window.isSecureContext}})),U.type==="device:boot-error"&&D(U.message),U.type==="device:booting"&&(u(!1),k(!1),C(!1),N(null),D(null),j(null)),U.type==="device:ready"&&(u(!0),r&&(k(!0),i.current({type:"app:install",sessionId:e,buildId:r}))),U.type==="app:install-done"&&(k(!1),C(!0)),U.type==="app:install-error"&&(k(!1),N(U.message)),U.type==="app:launch-done"&&X(!1),U.type==="app:launch-error"&&X(!1),U.type==="session:chrome"&&j(U.payload),U.type==="keyboard:toggled"){const{visible:z}=U.payload;O(z),Re(!1)}U.type==="open-url:done"&&at.success("Deeplink opened"),U.type==="open-url:error"&&at.error(U.message),U.type==="error"&&U.message==="Agent resources exhausted"&&at.error("Could not start session — this Mac is currently overloaded.",{description:"Go back and select a different Mac."})},[e,t,r]),De=o.useCallback(U=>{var K;const z=Ws(U);if(z&&z.codec===bn){ne(U.slice(_t));return}z&&z.codec===mt||d.current.push(z);const le=z?U.slice(_t):U,Q=z?{codec:z.codec,keyframe:z.keyframe,capturedAt:z.capturedAt,relayedAt:z.relayedAt}:void 0;(K=fe.current)==null||K.call(fe,le,Q)},[ne]),{send:re,connected:E}=sn(je,De);o.useLayoutEffect(()=>{i.current=re}),o.useEffect(()=>{E&&re({type:"session:start",sessionId:e})},[E,re,e]);const V=y!==null&&"framePng"in y?y:null,Y=y!==null&&!("framePng"in y)?y:null,ke={sessionId:e,buildId:r,send:re,connected:E,joined:m,deviceReady:g,installing:L,installed:A,installError:P,bootError:F,launching:B,setLaunching:X,binaryFrameHandlerRef:fe,onRecordingUploaded:a,swKeyboardVisible:$,swKeyboardPending:Z,onKbdToggle:()=>{Re(!0),re({type:"input:keyboard:toggle",sessionId:e})}};if(!V&&!Y)return n.jsxs("div",{className:"flex items-start justify-center gap-16",children:[n.jsx("div",{className:"flex flex-col items-center gap-0.5 rounded-2xl border bg-background/90 px-1.5 py-2.5 shrink-0 mt-3 opacity-40",children:Array.from({length:5}).map((U,z)=>n.jsx("div",{className:"h-8 w-8 rounded-md bg-muted animate-pulse"},z))}),n.jsxs("div",{className:"flex items-start gap-8",children:[n.jsx("div",{style:{background:"#1c1c1e",borderRadius:"34px",padding:"12px",flexShrink:0},children:n.jsx("div",{className:"animate-pulse bg-zinc-700",style:{width:324,height:720,borderRadius:"22px"}})}),n.jsx(Pt,{joined:m,fps:0,connected:E,deviceReady:g,bootError:F,installing:L,installError:P,keyboardActive:!1})]})]});const se=void 0;return n.jsxs(n.Fragment,{children:[V&&n.jsx(Ys,{...ke,chrome:V,perfHookRef:se}),Y&&n.jsx(Gs,{...ke,androidButtons:Y.buttons,screenWidth:Y.screenWidth,screenHeight:Y.screenHeight,cornerRadius:Y.cornerRadius,perfHookRef:se}),!1]})}const vn=o.forwardRef(({className:e,...t},r)=>n.jsx("textarea",{className:q("flex min-h-[80px] w-full rounded-md border border-input bg-background px-3 py-2 text-base ring-offset-background placeholder:text-muted-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50 md:text-sm",e),ref:r,...t}));vn.displayName="Textarea";function to(e,t){return o.useReducer((r,s)=>t[r][s]??r,e)}var At="ScrollArea",[wn]=nn(At),[no,xe]=wn(At),Sn=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,type:s="hover",dir:a,scrollHideDelay:i=600,...c}=e,[h,d]=o.useState(null),[m,p]=o.useState(null),[g,u]=o.useState(null),[y,j]=o.useState(null),[L,k]=o.useState(null),[A,C]=o.useState(0),[P,N]=o.useState(0),[F,D]=o.useState(!1),[B,X]=o.useState(!1),$=Fe(t,d),O=Gn(a);return n.jsx(no,{scope:r,type:s,dir:O,scrollHideDelay:i,scrollArea:h,viewport:m,onViewportChange:p,content:g,onContentChange:u,scrollbarX:y,onScrollbarXChange:j,scrollbarXEnabled:F,onScrollbarXEnabledChange:D,scrollbarY:L,onScrollbarYChange:k,scrollbarYEnabled:B,onScrollbarYEnabledChange:X,onCornerWidthChange:C,onCornerHeightChange:N,children:n.jsx($e.div,{dir:O,...c,ref:$,style:{position:"relative","--radix-scroll-area-corner-width":A+"px","--radix-scroll-area-corner-height":P+"px",...e.style}})})});Sn.displayName=At;var Rn="ScrollAreaViewport",jn=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,children:s,nonce:a,...i}=e,c=xe(Rn,r),h=o.useRef(null),d=Fe(t,h,c.onViewportChange);return n.jsxs(n.Fragment,{children:[n.jsx(ro,{nonce:a}),n.jsx($e.div,{"data-radix-scroll-area-viewport":"",...i,ref:d,style:{overflowX:c.scrollbarXEnabled?"scroll":"hidden",overflowY:c.scrollbarYEnabled?"scroll":"hidden",...e.style},children:n.jsx("div",{ref:c.onContentChange,style:{minWidth:"100%",display:"table"},children:s})})]})});jn.displayName=Rn;var ro=o.memo(({nonce:e})=>n.jsx("style",{dangerouslySetInnerHTML:{__html:"[data-radix-scroll-area-viewport]{scrollbar-width:none;-ms-overflow-style:none;-webkit-overflow-scrolling:touch;}[data-radix-scroll-area-viewport]::-webkit-scrollbar{display:none}"},nonce:e}),(e,t)=>e.nonce===t.nonce),Ne="ScrollAreaScrollbar",Dt=o.forwardRef((e,t)=>{const{forceMount:r,...s}=e,a=xe(Ne,e.__scopeScrollArea),{onScrollbarXEnabledChange:i,onScrollbarYEnabledChange:c}=a,h=e.orientation==="horizontal";return o.useEffect(()=>(h?i(!0):c(!0),()=>{h?i(!1):c(!1)}),[h,i,c]),a.type==="hover"?n.jsx(so,{...s,ref:t,forceMount:r}):a.type==="scroll"?n.jsx(oo,{...s,ref:t,forceMount:r}):a.type==="auto"?n.jsx(kn,{...s,ref:t,forceMount:r}):a.type==="always"?n.jsx(Lt,{...s,ref:t,"data-state":"visible"}):null});Dt.displayName=Ne;var so=o.forwardRef((e,t)=>{const{forceMount:r,...s}=e,a=xe(Ne,e.__scopeScrollArea),[i,c]=o.useState(!1);return o.useEffect(()=>{const h=a.scrollArea;let d=0;if(h){const m=()=>{window.clearTimeout(d),c(!0)},p=()=>{d=window.setTimeout(()=>c(!1),a.scrollHideDelay)};return h.addEventListener("pointerenter",m),h.addEventListener("pointerleave",p),()=>{window.clearTimeout(d),h.removeEventListener("pointerenter",m),h.removeEventListener("pointerleave",p)}}},[a.scrollArea,a.scrollHideDelay]),n.jsx(bt,{present:r||i,children:n.jsx(kn,{"data-state":i?"visible":"hidden",...s,ref:t})})}),oo=o.forwardRef((e,t)=>{const{forceMount:r,...s}=e,a=xe(Ne,e.__scopeScrollArea),i=e.orientation==="horizontal",c=vt(()=>d("SCROLL_END"),100),[h,d]=to("hidden",{hidden:{SCROLL:"scrolling"},scrolling:{SCROLL_END:"idle",POINTER_ENTER:"interacting"},interacting:{SCROLL:"interacting",POINTER_LEAVE:"idle"},idle:{HIDE:"hidden",SCROLL:"scrolling",POINTER_ENTER:"interacting"}});return o.useEffect(()=>{if(h==="idle"){const m=window.setTimeout(()=>d("HIDE"),a.scrollHideDelay);return()=>window.clearTimeout(m)}},[h,a.scrollHideDelay,d]),o.useEffect(()=>{const m=a.viewport,p=i?"scrollLeft":"scrollTop";if(m){let g=m[p];const u=()=>{const y=m[p];g!==y&&(d("SCROLL"),c()),g=y};return m.addEventListener("scroll",u),()=>m.removeEventListener("scroll",u)}},[a.viewport,i,d,c]),n.jsx(bt,{present:r||h!=="hidden",children:n.jsx(Lt,{"data-state":h==="hidden"?"hidden":"visible",...s,ref:t,onPointerEnter:Ue(e.onPointerEnter,()=>d("POINTER_ENTER")),onPointerLeave:Ue(e.onPointerLeave,()=>d("POINTER_LEAVE"))})})}),kn=o.forwardRef((e,t)=>{const r=xe(Ne,e.__scopeScrollArea),{forceMount:s,...a}=e,[i,c]=o.useState(!1),h=e.orientation==="horizontal",d=vt(()=>{if(r.viewport){const m=r.viewport.offsetWidth<r.viewport.scrollWidth,p=r.viewport.offsetHeight<r.viewport.scrollHeight;c(h?m:p)}},10);return et(r.viewport,d),et(r.content,d),n.jsx(bt,{present:s||i,children:n.jsx(Lt,{"data-state":i?"visible":"hidden",...a,ref:t})})}),Lt=o.forwardRef((e,t)=>{const{orientation:r="vertical",...s}=e,a=xe(Ne,e.__scopeScrollArea),i=o.useRef(null),c=o.useRef(0),[h,d]=o.useState({content:0,viewport:0,scrollbar:{size:0,paddingStart:0,paddingEnd:0}}),m=Tn(h.viewport,h.content),p={...s,sizes:h,onSizesChange:d,hasThumb:m>0&&m<1,onThumbChange:u=>i.current=u,onThumbPointerUp:()=>c.current=0,onThumbPointerDown:u=>c.current=u};function g(u,y){return fo(u,c.current,h,y)}return r==="horizontal"?n.jsx(ao,{...p,ref:t,onThumbPositionChange:()=>{if(a.viewport&&i.current){const u=a.viewport.scrollLeft,y=qt(u,h,a.dir);i.current.style.transform=`translate3d(${y}px, 0, 0)`}},onWheelScroll:u=>{a.viewport&&(a.viewport.scrollLeft=u)},onDragScroll:u=>{a.viewport&&(a.viewport.scrollLeft=g(u,a.dir))}}):r==="vertical"?n.jsx(io,{...p,ref:t,onThumbPositionChange:()=>{if(a.viewport&&i.current){const u=a.viewport.scrollTop,y=qt(u,h);i.current.style.transform=`translate3d(0, ${y}px, 0)`}},onWheelScroll:u=>{a.viewport&&(a.viewport.scrollTop=u)},onDragScroll:u=>{a.viewport&&(a.viewport.scrollTop=g(u))}}):null}),ao=o.forwardRef((e,t)=>{const{sizes:r,onSizesChange:s,...a}=e,i=xe(Ne,e.__scopeScrollArea),[c,h]=o.useState(),d=o.useRef(null),m=Fe(t,d,i.onScrollbarXChange);return o.useEffect(()=>{d.current&&h(getComputedStyle(d.current))},[d]),n.jsx(En,{"data-orientation":"horizontal",...a,ref:m,sizes:r,style:{bottom:0,left:i.dir==="rtl"?"var(--radix-scroll-area-corner-width)":0,right:i.dir==="ltr"?"var(--radix-scroll-area-corner-width)":0,"--radix-scroll-area-thumb-width":yt(r)+"px",...e.style},onThumbPointerDown:p=>e.onThumbPointerDown(p.x),onDragScroll:p=>e.onDragScroll(p.x),onWheelScroll:(p,g)=>{if(i.viewport){const u=i.viewport.scrollLeft+p.deltaX;e.onWheelScroll(u),An(u,g)&&p.preventDefault()}},onResize:()=>{d.current&&i.viewport&&c&&s({content:i.viewport.scrollWidth,viewport:i.viewport.offsetWidth,scrollbar:{size:d.current.clientWidth,paddingStart:xt(c.paddingLeft),paddingEnd:xt(c.paddingRight)}})}})}),io=o.forwardRef((e,t)=>{const{sizes:r,onSizesChange:s,...a}=e,i=xe(Ne,e.__scopeScrollArea),[c,h]=o.useState(),d=o.useRef(null),m=Fe(t,d,i.onScrollbarYChange);return o.useEffect(()=>{d.current&&h(getComputedStyle(d.current))},[d]),n.jsx(En,{"data-orientation":"vertical",...a,ref:m,sizes:r,style:{top:0,right:i.dir==="ltr"?0:void 0,left:i.dir==="rtl"?0:void 0,bottom:"var(--radix-scroll-area-corner-height)","--radix-scroll-area-thumb-height":yt(r)+"px",...e.style},onThumbPointerDown:p=>e.onThumbPointerDown(p.y),onDragScroll:p=>e.onDragScroll(p.y),onWheelScroll:(p,g)=>{if(i.viewport){const u=i.viewport.scrollTop+p.deltaY;e.onWheelScroll(u),An(u,g)&&p.preventDefault()}},onResize:()=>{d.current&&i.viewport&&c&&s({content:i.viewport.scrollHeight,viewport:i.viewport.offsetHeight,scrollbar:{size:d.current.clientHeight,paddingStart:xt(c.paddingTop),paddingEnd:xt(c.paddingBottom)}})}})}),[co,Cn]=wn(Ne),En=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,sizes:s,hasThumb:a,onThumbChange:i,onThumbPointerUp:c,onThumbPointerDown:h,onThumbPositionChange:d,onDragScroll:m,onWheelScroll:p,onResize:g,...u}=e,y=xe(Ne,r),[j,L]=o.useState(null),k=Fe(t,L),A=o.useRef(null),C=o.useRef(""),P=y.viewport,N=s.content-s.viewport,F=qe(p),D=qe(d),B=vt(g,10);function X($){if(A.current){const O=$.clientX-A.current.left,Z=$.clientY-A.current.top;m({x:O,y:Z})}}return o.useEffect(()=>{const $=O=>{const Z=O.target;(j==null?void 0:j.contains(Z))&&F(O,N)};return document.addEventListener("wheel",$,{passive:!1}),()=>document.removeEventListener("wheel",$,{passive:!1})},[P,j,N,F]),o.useEffect(D,[s,D]),et(j,B),et(y.content,B),n.jsx(co,{scope:r,scrollbar:j,hasThumb:a,onThumbChange:qe(i),onThumbPointerUp:qe(c),onThumbPositionChange:D,onThumbPointerDown:qe(h),children:n.jsx($e.div,{...u,ref:k,style:{position:"absolute",...u.style},onPointerDown:Ue(e.onPointerDown,$=>{$.button===0&&($.target.setPointerCapture($.pointerId),A.current=j.getBoundingClientRect(),C.current=document.body.style.webkitUserSelect,document.body.style.webkitUserSelect="none",y.viewport&&(y.viewport.style.scrollBehavior="auto"),X($))}),onPointerMove:Ue(e.onPointerMove,X),onPointerUp:Ue(e.onPointerUp,$=>{const O=$.target;O.hasPointerCapture($.pointerId)&&O.releasePointerCapture($.pointerId),document.body.style.webkitUserSelect=C.current,y.viewport&&(y.viewport.style.scrollBehavior=""),A.current=null})})})}),gt="ScrollAreaThumb",Nn=o.forwardRef((e,t)=>{const{forceMount:r,...s}=e,a=Cn(gt,e.__scopeScrollArea);return n.jsx(bt,{present:r||a.hasThumb,children:n.jsx(lo,{ref:t,...s})})}),lo=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,style:s,...a}=e,i=xe(gt,r),c=Cn(gt,r),{onThumbPositionChange:h}=c,d=Fe(t,c.onThumbChange),m=o.useRef(void 0),p=vt(()=>{m.current&&(m.current(),m.current=void 0)},100);return o.useEffect(()=>{const g=i.viewport;if(g){const u=()=>{if(p(),!m.current){const y=ho(g,h);m.current=y,h()}};return h(),g.addEventListener("scroll",u),()=>g.removeEventListener("scroll",u)}},[i.viewport,p,h]),n.jsx($e.div,{"data-state":c.hasThumb?"visible":"hidden",...a,ref:d,style:{width:"var(--radix-scroll-area-thumb-width)",height:"var(--radix-scroll-area-thumb-height)",...s},onPointerDownCapture:Ue(e.onPointerDownCapture,g=>{const y=g.target.getBoundingClientRect(),j=g.clientX-y.left,L=g.clientY-y.top;c.onThumbPointerDown({x:j,y:L})}),onPointerUp:Ue(e.onPointerUp,c.onThumbPointerUp)})});Nn.displayName=gt;var Mt="ScrollAreaCorner",_n=o.forwardRef((e,t)=>{const r=xe(Mt,e.__scopeScrollArea),s=!!(r.scrollbarX&&r.scrollbarY);return r.type!=="scroll"&&s?n.jsx(uo,{...e,ref:t}):null});_n.displayName=Mt;var uo=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,...s}=e,a=xe(Mt,r),[i,c]=o.useState(0),[h,d]=o.useState(0),m=!!(i&&h);return et(a.scrollbarX,()=>{var g;const p=((g=a.scrollbarX)==null?void 0:g.offsetHeight)||0;a.onCornerHeightChange(p),d(p)}),et(a.scrollbarY,()=>{var g;const p=((g=a.scrollbarY)==null?void 0:g.offsetWidth)||0;a.onCornerWidthChange(p),c(p)}),m?n.jsx($e.div,{...s,ref:t,style:{width:i,height:h,position:"absolute",right:a.dir==="ltr"?0:void 0,left:a.dir==="rtl"?0:void 0,bottom:0,...e.style}}):null});function xt(e){return e?parseInt(e,10):0}function Tn(e,t){const r=e/t;return isNaN(r)?0:r}function yt(e){const t=Tn(e.viewport,e.content),r=e.scrollbar.paddingStart+e.scrollbar.paddingEnd,s=(e.scrollbar.size-r)*t;return Math.max(s,18)}function fo(e,t,r,s="ltr"){const a=yt(r),i=a/2,c=t||i,h=a-c,d=r.scrollbar.paddingStart+c,m=r.scrollbar.size-r.scrollbar.paddingEnd-h,p=r.content-r.viewport,g=s==="ltr"?[0,p]:[p*-1,0];return Pn([d,m],g)(e)}function qt(e,t,r="ltr"){const s=yt(t),a=t.scrollbar.paddingStart+t.scrollbar.paddingEnd,i=t.scrollbar.size-a,c=t.content-t.viewport,h=i-s,d=r==="ltr"?[0,c]:[c*-1,0],m=pr(e,d);return Pn([0,c],[0,h])(m)}function Pn(e,t){return r=>{if(e[0]===e[1]||t[0]===t[1])return t[0];const s=(t[1]-t[0])/(e[1]-e[0]);return t[0]+s*(r-e[0])}}function An(e,t){return e>0&&e<t}var ho=(e,t=()=>{})=>{let r={left:e.scrollLeft,top:e.scrollTop},s=0;return(function a(){const i={left:e.scrollLeft,top:e.scrollTop},c=r.left!==i.left,h=r.top!==i.top;(c||h)&&t(),r=i,s=window.requestAnimationFrame(a)})(),()=>window.cancelAnimationFrame(s)};function vt(e,t){const r=qe(e),s=o.useRef(0);return o.useEffect(()=>()=>window.clearTimeout(s.current),[]),o.useCallback(()=>{window.clearTimeout(s.current),s.current=window.setTimeout(r,t)},[r,t])}function et(e,t){const r=qe(t);qn(()=>{let s=0;if(e){const a=new ResizeObserver(()=>{cancelAnimationFrame(s),s=window.requestAnimationFrame(r)});return a.observe(e),()=>{window.cancelAnimationFrame(s),a.unobserve(e)}}},[e,r])}var Dn=Sn,po=jn,mo=_n;const Ln=o.forwardRef(({className:e,children:t,...r},s)=>n.jsxs(Dn,{ref:s,className:q("relative overflow-hidden",e),...r,children:[n.jsx(po,{className:"h-full w-full rounded-[inherit]",children:t}),n.jsx(Mn,{}),n.jsx(mo,{})]}));Ln.displayName=Dn.displayName;const Mn=o.forwardRef(({className:e,orientation:t="vertical",...r},s)=>n.jsx(Dt,{ref:s,orientation:t,className:q("flex touch-none select-none transition-colors",t==="vertical"&&"h-full w-2.5 border-l border-l-transparent p-[1px]",t==="horizontal"&&"h-2.5 flex-col border-t border-t-transparent p-[1px]",e),...r,children:n.jsx(Nn,{className:"relative flex-1 rounded-full bg-border"})}));Mn.displayName=Dt.displayName;function Hn(e){return/[Zz]|[+-]\d{2}/.test(e)?new Date(e):new Date(e.replace(" ","T")+"Z")}function go(e){const t=new Map;for(const a of e){const i=Hn(a.created_at).toDateString();t.has(i)||t.set(i,[]),t.get(i).push(a)}const r=new Date().toDateString(),s=new Date(Date.now()-864e5).toDateString();return Array.from(t.entries()).map(([a,i])=>{let c;if(a===r)c="Today";else if(a===s)c="Yesterday";else{const h=new Date(a);c=h.toLocaleDateString(void 0,{month:"short",day:"numeric",...h.getFullYear()!==new Date().getFullYear()?{year:"numeric"}:{}})}return{label:c,items:i}})}function xo(e){return Hn(e).toLocaleTimeString(void 0,{hour:"numeric",minute:"2-digit"})}const bo=5*1024*1024,yo=["image/png","image/jpeg","image/webp"];function vo({buildId:e}){const[t,r]=o.useState([]),[s,a]=o.useState(""),[i,c]=o.useState(null),[h,d]=o.useState(!1),[m,p]=o.useState(""),g=o.useRef(null),u=o.useRef({});function y(){fetch(`/api/v1/comments?build_id=${e}`,{credentials:"include"}).then(C=>C.ok?C.json():[]).then(r)}o.useEffect(()=>{y()},[e]),o.useEffect(()=>{const C=window.location.hash;if(!C.startsWith("#comment-"))return;const P=Number(C.replace("#comment-","")),N=u.current[P];if(!N)return;N.scrollIntoView({behavior:"smooth"});const F=document.documentElement.classList.contains("dark");N.style.backgroundColor=F?"rgb(0 112 243 / 0.18)":"#d3e5ff",setTimeout(()=>{N.style.backgroundColor=""},2e3)},[t]);function j(C){const P=`${location.origin}${location.pathname}${location.search}#comment-${C}`;navigator.clipboard.writeText(P).then(()=>at.success("Link copied")).catch(()=>at.error("Could not copy link"))}function L(C){if(p(""),!yo.includes(C.type)){p("Only png, jpg, webp allowed");return}if(C.size>bo){p("Max 5MB");return}c(C)}async function k(C){if(C.preventDefault(),!s.trim()&&!i)return;d(!0);const P=new FormData;P.append("build_id",String(e)),P.append("body",s),i&&P.append("attachment",i),(await fetch("/api/v1/comments",{method:"POST",credentials:"include",body:P})).ok&&(a(""),c(null),y()),d(!1)}const A=go(t);return n.jsxs("div",{className:"flex h-full flex-col gap-3 px-1",children:[n.jsx(Ln,{className:"flex-1 rounded-md border",children:n.jsx("div",{className:"p-3",children:t.length===0?n.jsx("p",{className:"text-sm text-muted-foreground text-center py-8",children:"No comments yet."}):n.jsx("div",{className:"flex flex-col",children:A.map(({label:C,items:P})=>n.jsxs("div",{children:[n.jsxs("div",{className:"flex items-center gap-2 py-3",children:[n.jsx("div",{className:"h-px flex-1 bg-border"}),n.jsx("span",{className:"text-[11px] font-medium text-muted-foreground px-1 select-none",children:C}),n.jsx("div",{className:"h-px flex-1 bg-border"})]}),n.jsx("div",{className:"flex flex-col gap-4",children:P.map(N=>n.jsxs("div",{id:`comment-${N.id}`,ref:F=>{u.current[N.id]=F},className:"group flex gap-2.5 rounded-md px-2 py-1.5 transition-all",children:[n.jsx("div",{className:"mt-0.5 shrink-0",children:n.jsx(Jn,{name:N.author,avatarUrl:N.authorAvatarUrl,size:28})}),n.jsxs("div",{className:"flex-1 min-w-0",children:[n.jsxs("div",{className:"flex items-center gap-1.5",children:[n.jsx("span",{className:"text-sm font-semibold leading-none",children:N.author}),n.jsx("span",{className:"text-[11px] text-muted-foreground leading-none",children:xo(N.created_at)}),n.jsx(ee,{variant:"ghost",size:"icon",className:"h-4 w-4 ml-0.5 opacity-0 group-hover:opacity-50 hover:!opacity-100 transition-opacity",onClick:()=>j(N.id),children:n.jsx(un,{className:"h-3 w-3"})})]}),n.jsx("p",{className:"text-sm leading-relaxed whitespace-pre-wrap mt-1",children:N.body}),N.attachments.map(F=>n.jsx("a",{href:F.file_path,target:"_blank",rel:"noreferrer",className:"mt-1.5 block",children:n.jsx("img",{src:F.file_path,alt:"attachment",className:"max-h-48 rounded border object-contain"})},F.id))]})]},N.id))})]},C))})})}),n.jsx("div",{className:"pb-1",children:n.jsx("form",{onSubmit:k,children:n.jsxs("div",{className:"rounded-xl border border-input bg-background ring-offset-background transition-shadow focus-within:outline-none focus-within:ring-2 focus-within:ring-ring focus-within:ring-offset-2",children:[n.jsx(vn,{placeholder:"Leave a comment…",value:s,onChange:C=>a(C.target.value),className:"min-h-16 resize-none border-0 bg-transparent shadow-none focus-visible:ring-0 focus-visible:ring-offset-0 text-sm"}),(i||m)&&n.jsxs("div",{className:"px-3 -mt-1 pb-1",children:[i&&n.jsx("p",{className:"text-xs text-muted-foreground",children:i.name}),m&&n.jsx("p",{className:"text-xs text-destructive",children:m})]}),n.jsxs("div",{className:"flex items-center gap-2 px-2 py-2",children:[n.jsx(ee,{type:"button",variant:"ghost",size:"icon",className:"h-7 w-7 text-muted-foreground",onClick:()=>{var C;return(C=g.current)==null?void 0:C.click()},children:n.jsx(Dr,{className:"h-4 w-4"})}),n.jsx("input",{ref:g,type:"file",accept:"image/png,image/jpeg,image/webp",className:"hidden",onChange:C=>{var N;const P=(N=C.target.files)==null?void 0:N[0];P&&L(P)}}),n.jsx("div",{className:"flex-1"}),n.jsx(ee,{type:"submit",size:"icon",className:"h-7 w-7 rounded-full",disabled:h||!s.trim()&&!i,children:n.jsx(jr,{className:"h-3.5 w-3.5"})})]})]})})})]})}function wo(e){return e<1024*1024?`${(e/1024).toFixed(0)} KB`:`${(e/1024/1024).toFixed(1)} MB`}function So(e){return new Date(e).toLocaleString(void 0,{month:"short",day:"numeric",hour:"2-digit",minute:"2-digit"})}function Ro(e){const t=new Date(e).getTime()-Date.now();if(t<=0)return{label:"Expired",urgent:!0};const r=Math.floor(t/36e5);return r<1?{label:"< 1 hour left",urgent:!0}:r<24?{label:`Expires in ${r}h`,urgent:r<6}:{label:`Expires in ${Math.floor(r/24)}d`,urgent:!1}}function jo({buildId:e,refreshKey:t}){const[r,s]=o.useState([]),[a,i]=o.useState(!0),[c,h]=o.useState(!1);return o.useEffect(()=>{i(!0),h(!1);const d=setTimeout(()=>h(!0),250);return fetch(`/api/v1/recordings?buildId=${e}`,{credentials:"include"}).then(m=>m.ok?m.json():[]).then(m=>s(m)).catch(()=>s([])).finally(()=>{clearTimeout(d),i(!1)}),()=>clearTimeout(d)},[e,t]),a?c?n.jsx("p",{className:"text-xs text-muted-foreground",children:"Loading recordings…"}):null:r.length===0?n.jsx("p",{className:"py-8 text-center text-sm text-muted-foreground",children:"No recordings yet."}):n.jsx("div",{className:"flex flex-col gap-2",children:r.map(d=>{const m=Ro(d.expiresAt);return n.jsxs("div",{className:"flex items-center justify-between rounded-md border border-border px-3 py-2 text-sm",children:[n.jsxs("div",{className:"flex flex-col gap-0.5 min-w-0",children:[n.jsx("span",{className:"text-xs font-medium truncate",children:So(d.createdAt)}),n.jsxs("span",{className:`text-xs ${m.urgent?"text-destructive":"text-muted-foreground"}`,children:[m.label," · ",wo(d.fileSize)]})]}),n.jsx(ee,{variant:"ghost",size:"icon",className:"h-7 w-7 shrink-0 ml-2",title:"Download",onClick:()=>{const p=document.createElement("a");p.href=d.url,p.download="",p.click()},children:n.jsx(Nr,{className:"h-3.5 w-3.5"})})]},d.id)})})}function ko({buildId:e,recordingsRefreshKey:t=0}){return n.jsxs(lr,{defaultValue:"comments",className:"flex h-full flex-col",children:[n.jsx("div",{className:"shrink-0 px-1",children:n.jsxs(ur,{className:"w-full",children:[n.jsxs(Bt,{value:"comments",className:"flex-1 gap-1.5",children:[n.jsx(Br,{className:"h-3.5 w-3.5"}),"Comments"]}),n.jsxs(Bt,{value:"recordings",className:"flex-1 gap-1.5",children:[n.jsx(Tr,{className:"h-3.5 w-3.5"}),"Recordings"]})]})}),n.jsx(zt,{value:"comments",className:"mt-3 min-h-0 flex-1 overflow-hidden",children:n.jsx(vo,{buildId:e})}),n.jsx(zt,{value:"recordings",className:"mt-3 min-h-0 flex-1 overflow-y-auto",children:n.jsx(jo,{buildId:e,refreshKey:t})})]})}const Un=o.forwardRef(({...e},t)=>n.jsx("nav",{ref:t,"aria-label":"breadcrumb",...e}));Un.displayName="Breadcrumb";const Fn=o.forwardRef(({className:e,...t},r)=>n.jsx("ol",{ref:r,className:q("flex flex-wrap items-center gap-1.5 break-words text-sm text-muted-foreground sm:gap-2.5",e),...t}));Fn.displayName="BreadcrumbList";const ot=o.forwardRef(({className:e,...t},r)=>n.jsx("li",{ref:r,className:q("inline-flex items-center gap-1.5",e),...t}));ot.displayName="BreadcrumbItem";const dt=o.forwardRef(({asChild:e,className:t,...r},s)=>{const a=e?Zn:"a";return n.jsx(a,{ref:s,className:q("transition-colors hover:text-foreground cursor-pointer",t),...r})});dt.displayName="BreadcrumbLink";const ft=o.forwardRef(({className:e,...t},r)=>n.jsx("span",{ref:r,role:"link","aria-disabled":"true","aria-current":"page",className:q("font-medium text-foreground",e),...t}));ft.displayName="BreadcrumbPage";const ht=({children:e,className:t,...r})=>n.jsx("li",{role:"presentation","aria-hidden":"true",className:q("[&>svg]:h-3.5 [&>svg]:w-3.5",t),...r,children:e??n.jsx(Qn,{})});ht.displayName="BreadcrumbSeparator";var wt="Switch",[Co]=nn(wt),[Eo,Ht]=Co(wt);function No(e){const{__scopeSwitch:t,checked:r,children:s,defaultChecked:a,disabled:i,form:c,name:h,onCheckedChange:d,required:m,value:p="on",internal_do_not_use_render:g}=e,[u,y]=er({prop:r,defaultProp:a??!1,onChange:d,caller:wt}),[j,L]=o.useState(null),[k,A]=o.useState(null),C=o.useRef(!1),P=j?!!c||!!j.closest("form"):!0,N={checked:u,setChecked:y,disabled:i,control:j,setControl:L,name:h,form:c,value:p,hasConsumerStoppedPropagationRef:C,required:m,defaultChecked:a,isFormControl:P,bubbleInput:k,setBubbleInput:A};return n.jsx(Eo,{scope:t,...N,children:_o(g)?g(N):s})}var $n="SwitchTrigger",In=o.forwardRef(({__scopeSwitch:e,onClick:t,...r},s)=>{const{value:a,disabled:i,checked:c,required:h,setControl:d,setChecked:m,hasConsumerStoppedPropagationRef:p,isFormControl:g,bubbleInput:u}=Ht($n,e),y=Fe(s,d);return n.jsx($e.button,{type:"button",role:"switch","aria-checked":c,"aria-required":h,"data-state":Vn(c),"data-disabled":i?"":void 0,disabled:i,value:a,...r,ref:y,onClick:Ue(t,j=>{m(L=>!L),u&&g&&(p.current=j.isPropagationStopped(),p.current||j.stopPropagation())})})});In.displayName=$n;var Ut=o.forwardRef((e,t)=>{const{__scopeSwitch:r,name:s,checked:a,defaultChecked:i,required:c,disabled:h,value:d,onCheckedChange:m,form:p,...g}=e;return n.jsx(No,{__scopeSwitch:r,checked:a,defaultChecked:i,disabled:h,required:c,onCheckedChange:m,name:s,form:p,value:d,internal_do_not_use_render:({isFormControl:u})=>n.jsxs(n.Fragment,{children:[n.jsx(In,{...g,ref:t,__scopeSwitch:r}),u&&n.jsx(Wn,{__scopeSwitch:r})]})})});Ut.displayName=wt;var Bn="SwitchThumb",zn=o.forwardRef((e,t)=>{const{__scopeSwitch:r,...s}=e,a=Ht(Bn,r);return n.jsx($e.span,{"data-state":Vn(a.checked),"data-disabled":a.disabled?"":void 0,...s,ref:t})});zn.displayName=Bn;var On="SwitchBubbleInput",Wn=o.forwardRef(({__scopeSwitch:e,...t},r)=>{const{control:s,hasConsumerStoppedPropagationRef:a,checked:i,defaultChecked:c,required:h,disabled:d,name:m,value:p,form:g,bubbleInput:u,setBubbleInput:y}=Ht(On,e),j=Fe(r,y),L=mr(i),k=tr(s);o.useEffect(()=>{const C=u;if(!C)return;const P=window.HTMLInputElement.prototype,F=Object.getOwnPropertyDescriptor(P,"checked").set,D=!a.current;if(L!==i&&F){const B=new Event("click",{bubbles:D});F.call(C,i),C.dispatchEvent(B)}},[u,L,i,a]);const A=o.useRef(i);return n.jsx($e.input,{type:"checkbox","aria-hidden":!0,defaultChecked:c??A.current,required:h,disabled:d,name:m,value:p,form:g,...t,tabIndex:-1,ref:j,style:{...t.style,...k,position:"absolute",pointerEvents:"none",opacity:0,margin:0,transform:"translateX(-100%)"}})});Wn.displayName=On;function _o(e){return typeof e=="function"}function Vn(e){return e?"checked":"unchecked"}const Xn=o.forwardRef(({className:e,...t},r)=>n.jsx(Ut,{className:q("peer inline-flex h-6 w-11 shrink-0 cursor-pointer items-center rounded-full border-2 border-transparent transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 focus-visible:ring-offset-background disabled:cursor-not-allowed disabled:opacity-50 data-[state=checked]:bg-primary data-[state=unchecked]:bg-input",e),...t,ref:r,children:n.jsx(zn,{className:q("pointer-events-none block h-5 w-5 rounded-full bg-background shadow-lg ring-0 transition-transform data-[state=checked]:translate-x-5 data-[state=unchecked]:translate-x-0")})}));Xn.displayName=Ut.displayName;const Jt=70,Zt=80;function To(e,t){if(!e||t)return"unknown";const r=e.memUsedMB/e.memTotalMB*100;return e.cpuPercent>Zt||r>Zt?"overloaded":e.cpuPercent>=Jt||r>=Jt?"warning":"healthy"}function Uo(){const[e]=en(),t=nr(),r=e.get("id"),{build:s}=ns(r),[a,i]=o.useState(0),c=(s==null?void 0:s.platform)??"ios",{sessions:h,selectedAgent:d,setSelectedAgent:m,activeSessionId:p,deviceId:g,booting:u,status:y,connected:j,agentGroups:L,startDevice:k,resetDevice:A,handleBack:C,handleBackToMacs:P}=rs(c),N=L.find(E=>E.agentName===d),{osVersions:F,osVersion:D,setOsVersion:B,deviceSearch:X,setDeviceSearch:$,versionedDevices:O,resetMode:Z,setResetMode:Re}=ss(N,c),ne=h.flatMap(E=>E.devices).find(E=>E.id===g),je=ne?`${ne.name}${ne.osVersion?` · ${ne.osVersion}`:""}`:"",De=o.useCallback(()=>i(E=>E+1),[]),{setNode:re}=rr();return o.useEffect(()=>{if(s)return re(n.jsxs("div",{className:"flex items-center gap-3",children:[n.jsx(Un,{children:n.jsxs(Fn,{children:[n.jsx(ot,{children:n.jsx(dt,{asChild:!0,children:n.jsx("button",{onClick:()=>t(`/app-center?appId=${s.app_id}`),children:s.name})})}),n.jsx(ht,{}),n.jsx(ot,{children:d?n.jsx(dt,{asChild:!0,children:n.jsx("button",{onClick:P,children:It(s)})}):n.jsx(ft,{children:It(s)})}),d&&n.jsxs(n.Fragment,{children:[n.jsx(ht,{}),n.jsx(ot,{children:p?n.jsx(dt,{asChild:!0,children:n.jsx("button",{onClick:C,children:d})}):n.jsx(ft,{children:d})})]}),p&&n.jsxs(n.Fragment,{children:[n.jsx(ht,{}),n.jsx(ot,{children:n.jsx(ft,{children:je})})]})]})}),!d&&s.status_label&&n.jsx(vr,{tone:ir[s.status_label],children:s.status_label})]})),()=>re(null)},[s,d,p,je,t,C,P,re]),n.jsxs("div",{className:"flex h-full min-h-0 gap-6 p-6",children:[n.jsx("div",{className:"flex flex-col gap-3 flex-1 min-w-0 min-h-0",children:n.jsx("div",{className:"flex-1 min-h-0 overflow-auto -ml-1 pl-1 -mr-4 pr-4",children:p?n.jsx("div",{className:"min-h-full flex items-center justify-center py-6 px-8 min-w-max",children:n.jsx(eo,{sessionId:p,deviceId:g,buildId:s==null?void 0:s.id,resetMode:Z,onRecordingUploaded:De})}):d?n.jsxs("div",{className:"flex flex-col gap-5",children:[n.jsxs("div",{className:"flex items-center gap-3",children:[n.jsx("button",{onClick:P,className:"text-sm text-muted-foreground hover:text-foreground transition-colors",children:"← All Macs"}),n.jsx("h1",{className:"text-xl font-semibold tracking-tight",children:"Select device"})]}),n.jsxs("div",{className:"flex items-center gap-2",children:[n.jsx(cr,{placeholder:"Search device…",value:X,onChange:$}),F.length>0&&n.jsxs(gr,{value:D||"__all__",onValueChange:E=>{B(E==="__all__"?"":E),A()},children:[n.jsx(xr,{className:"h-8 w-36 shrink-0",children:n.jsx(br,{})}),n.jsxs(yr,{children:[n.jsx(Ot,{value:"__all__",children:"Any version"}),F.map(E=>n.jsx(Ot,{value:E,children:E},E))]})]}),n.jsx(Ct,{children:n.jsxs(ve,{children:[n.jsxs("div",{className:"ml-auto flex items-center gap-2 shrink-0",children:[n.jsx(we,{asChild:!0,children:n.jsxs(sr,{htmlFor:"reset-mode",className:"flex items-center gap-1 text-sm cursor-pointer whitespace-nowrap",children:[n.jsx(Mr,{className:"h-3.5 w-3.5 text-muted-foreground"}),"Full reset"]})}),n.jsx(Xn,{id:"reset-mode",checked:Z==="full-erase",onCheckedChange:E=>Re(E?"full-erase":"app-only")})]}),n.jsx(Se,{children:Z==="full-erase"?"Erase all data before booting":"Keep existing data"})]})})]}),O.length===0?n.jsx("p",{className:"text-sm text-muted-foreground",children:j?"No devices available for this OS.":"Connecting to relay…"}):n.jsx("div",{className:"grid grid-cols-1 lg:grid-cols-2 2xl:grid-cols-3 gap-2",children:O.map(E=>{const V=E.status==="booted",Y=E.busy,ce=Y?"In use":V?"Booted":"Available",ke=Y?"bg-amber-400":V?"bg-emerald-400":"bg-muted-foreground/40";return n.jsxs("button",{disabled:Y||u||!j,onClick:()=>k(E),className:q("flex flex-col gap-3 rounded-lg border p-3 text-left transition-colors min-h-[100px]","hover:bg-accent disabled:cursor-not-allowed disabled:opacity-50"),children:[n.jsx("span",{className:"text-sm font-medium leading-tight",children:E.name}),E.osVersion&&n.jsx("span",{className:"font-mono text-xs text-muted-foreground",children:E.osVersion}),n.jsxs("span",{className:"flex items-center gap-1.5 text-xs text-muted-foreground",children:[n.jsx("span",{className:q("inline-block h-1.5 w-1.5 rounded-full",ke)}),ce]})]},E.id)})}),y&&n.jsx("p",{className:"text-sm text-muted-foreground",children:y})]}):n.jsxs("div",{className:"flex flex-col gap-5",children:[n.jsx("h1",{className:"text-xl font-semibold tracking-tight",children:"Select Mac"}),L.length===0?n.jsx("p",{className:"text-sm text-muted-foreground",children:j?`No agents available for ${c}.`:"Connecting to relay…"}):n.jsx("div",{className:"grid grid-cols-1 lg:grid-cols-2 2xl:grid-cols-3 gap-2",children:L.map(E=>{const V=E.resources,Y=V?Date.now()-V.reportedAt>3e4:!1,ce=E.devices.filter(le=>le.platform===c).length,ke=(V==null?void 0:V.cpuPercent)??0,se=V?V.memUsedMB/V.memTotalMB*100:0,U=To(V,Y),z=U==="overloaded";return n.jsx(Ct,{children:n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx("span",{tabIndex:z?0:void 0,className:z?"cursor-not-allowed":void 0,children:n.jsxs("button",{disabled:z,"aria-disabled":z,onClick:()=>m(E.agentName??null),className:q("flex flex-col gap-3 rounded-lg border p-3 text-left transition-colors min-h-[100px] w-full",z?"pointer-events-none":"hover:bg-accent"),children:[n.jsxs("div",{className:"flex items-start justify-between gap-2",children:[n.jsxs("div",{className:"flex items-center gap-2 min-w-0",children:[n.jsx(Po,{health:U}),n.jsx("span",{className:"text-sm font-medium leading-tight truncate",children:E.agentName??"Unknown"})]}),Y&&n.jsx("span",{className:"shrink-0 text-[10px] font-medium text-amber-500",children:"Stale"})]}),n.jsxs("div",{className:"flex items-center gap-1.5 text-xs text-muted-foreground",children:[n.jsxs("span",{children:[ce," device",ce!==1?"s":""]}),V&&n.jsxs(n.Fragment,{children:[n.jsx("span",{children:"·"}),n.jsxs("span",{children:[V.slotsAvailable,"/",V.slotsTotal," slots"]})]})]}),V&&!Y&&n.jsxs("div",{className:"flex flex-col gap-1.5 w-full",children:[n.jsx(Qt,{label:"CPU",percent:ke,colorClass:"bg-blue-400"}),n.jsx(Qt,{label:"RAM",percent:se,colorClass:"bg-violet-400"})]})]})})}),z&&n.jsx(Se,{children:"This Mac is currently overloaded. Try again later."})]})},E.agentName)})})]})})}),r&&n.jsxs(n.Fragment,{children:[n.jsx(tn,{orientation:"vertical",className:"h-auto"}),n.jsx("div",{className:"w-80 shrink-0 h-full",children:n.jsx(ko,{buildId:Number(r),recordingsRefreshKey:a})})]})]})}function Po({health:e}){const t={unknown:"bg-muted-foreground/40",healthy:"bg-emerald-400",warning:"bg-amber-400",overloaded:"bg-red-500"}[e];return n.jsx("span",{"data-testid":"resource-health-dot",className:q("inline-block h-2 w-2 shrink-0 rounded-full",t)})}function Qt({label:e,percent:t,colorClass:r}){return n.jsxs("div",{className:"flex flex-col gap-0.5",children:[n.jsxs("div",{className:"flex justify-between text-[10px] text-muted-foreground",children:[n.jsx("span",{children:e}),n.jsxs("span",{children:[t.toFixed(0),"%"]})]}),n.jsx("div",{className:"h-1 w-full rounded-full bg-muted overflow-hidden",children:n.jsx("div",{className:q("h-full rounded-full transition-all",r),style:{width:`${Math.min(100,t)}%`}})})]})}export{Uo as QASession};
|
|
130
|
+
}`;function Rt(e,t,r,s){const a=e.createTexture();return e.activeTexture(e.TEXTURE0+t),e.bindTexture(e.TEXTURE_2D,a),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_MIN_FILTER,e.LINEAR),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_MAG_FILTER,e.LINEAR),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_WRAP_S,e.CLAMP_TO_EDGE),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_WRAP_T,e.CLAMP_TO_EDGE),e.uniform1i(e.getUniformLocation(s,r),t),a}function Ss(e){const t=e.getContext("webgl2",{alpha:!1,antialias:!1,powerPreference:"high-performance",preserveDrawingBuffer:!0});if(!t)return null;const r=(u,b)=>{const k=t.createShader(u);return t.shaderSource(k,b),t.compileShader(k),k},s=t.createProgram(),a=r(t.VERTEX_SHADER,vs),i=r(t.FRAGMENT_SHADER,ws);t.attachShader(s,a),t.attachShader(s,i),t.linkProgram(s),t.deleteShader(a),t.deleteShader(i),t.useProgram(s);const c=t.createVertexArray();t.bindVertexArray(c);const h=t.createBuffer();t.bindBuffer(t.ARRAY_BUFFER,h),t.bufferData(t.ARRAY_BUFFER,new Float32Array([-1,-1,1,-1,-1,1,-1,1,1,-1,1,1]),t.STATIC_DRAW);const d=t.getAttribLocation(s,"a_pos");t.enableVertexAttribArray(d),t.vertexAttribPointer(d,2,t.FLOAT,!1,0,0),t.bindVertexArray(null),t.pixelStorei(t.UNPACK_ALIGNMENT,1);const m=Rt(t,0,"u_texY",s),p=Rt(t,1,"u_texU",s),x=Rt(t,2,"u_texV",s);return{gl:t,program:s,texY:m,texU:p,texV:x,vao:c}}class Rs{constructor(t){this.canvas=t,this.state=null}init(){return this.state=Ss(this.canvas),this.state!==null}drawI420(t,r,s){const a=this.state;if(!a)return null;const{gl:i}=a,c=r+1>>1,h=s+1>>1,d=r*s,m=c*h,p=t.subarray(0,d),x=t.subarray(d,d+m),u=t.subarray(d+m,d+2*m);(this.canvas.width!==r||this.canvas.height!==s)&&(this.canvas.width=r,this.canvas.height=s,i.viewport(0,0,r,s));const b=(k,L,C,N,j)=>{i.activeTexture(i.TEXTURE0+k),i.bindTexture(i.TEXTURE_2D,L),i.texImage2D(i.TEXTURE_2D,0,i.R8,C,N,0,i.RED,i.UNSIGNED_BYTE,j)};return b(0,a.texY,r,s,p),b(1,a.texU,c,h,x),b(2,a.texV,c,h,u),i.bindVertexArray(a.vao),i.drawArrays(i.TRIANGLES,0,6),i.bindVertexArray(null),{width:r,height:s}}dispose(){const t=this.state;t&&(t.gl.deleteTexture(t.texY),t.gl.deleteTexture(t.texU),t.gl.deleteTexture(t.texV),t.gl.deleteVertexArray(t.vao),t.gl.deleteProgram(t.program),this.state=null)}}const js=0;function ks(e){const t=new Rs(e);return t.init(),t}function Cs(){return new Worker(new URL("/assets/tinyh264.worker-DiJ50Hai.js",import.meta.url),{type:"module"})}class Es{constructor(t=ks,r=Cs){this.ready=!1,this.pending=[],this._size=null,this.canvas=document.createElement("canvas"),this.renderer=t(this.canvas),this.worker=r(),this.worker.onmessage=s=>this.onMessage(s.data)}get surface(){return this.canvas}get size(){return this._size}onResize(t){this.resizeCb=t}onDecodedFrame(t){this.decodedCb=t}decode(t){if(!this.ready){this.pending.push(t);return}this.post(t)}close(){this.worker.terminate(),this.renderer.dispose()}post(t){this.worker.postMessage({type:"decode",data:t,offset:0,length:t.byteLength,renderStateId:js},[t])}onMessage(t){var s,a;if(t.type==="decoderReady"){this.ready=!0;for(const i of this.pending)this.post(i);this.pending.length=0;return}const r=this.renderer.drawI420(new Uint8Array(t.data),t.width,t.height);r&&((s=this.decodedCb)==null||s.call(this,performance.now()),(!this._size||this._size.width!==r.width||this._size.height!==r.height)&&(this._size=r,(a=this.resizeCb)==null||a.call(this,r)))}}function Tt(){const e=typeof window<"u";let t=!1;try{t=!!document.createElement("canvas").getContext("webgl2")}catch{t=!1}return{secureContext:e&&window.isSecureContext===!0,webCodecs:e&&"VideoDecoder"in window,webgl2:t,wasm:typeof WebAssembly<"u"&&typeof Worker<"u"}}function Ns(e=Tt()){return e.secureContext&&e.webCodecs&&e.webgl2?new ys:e.wasm&&e.webgl2?new Es:null}function _s(e=Tt()){return e.secureContext&&e.webCodecs&&e.webgl2||e.wasm&&e.webgl2}function Ts(e=Tt()){return e.secureContext&&e.webCodecs&&e.webgl2?"high":e.wasm&&e.webgl2?"standard":"unsupported"}const Vt="tapflow.perfModeNoticeDismissed",Ps="https://www.tapflow.dev/reference/configuration#https-secure-context";function As(e,t){return e==="standard"&&!t}function Ds({open:e,onOpenChange:t}){return n.jsx(on,{open:e,onOpenChange:t,children:n.jsxs(an,{className:"sm:max-w-[440px]",children:[n.jsxs(dr,{children:[n.jsx(cn,{children:"Streaming in Standard mode"}),n.jsxs(fr,{className:"space-y-3 pt-1",children:[n.jsx("span",{className:"block",children:"This screen is running in Standard mode. For a faster, smoother picture, switch to Smooth."}),n.jsx("span",{className:"block",children:"Smooth needs the relay served over HTTPS. If you didn't set up tapflow, ask whoever did."})]})]}),n.jsxs(hr,{children:[n.jsx(ee,{variant:"outline",onClick:()=>window.open(Ps,"_blank","noopener,noreferrer"),children:"How to enable"}),n.jsx(ee,{onClick:()=>t(!1),children:"Got it"})]})]})})}const Ls={high:"Smooth",standard:"Standard",unsupported:null};function Ms(e){const{connected:t,joined:r,bootError:s,deviceReady:a,installing:i,installError:c}=e;return t?r?s?`Boot failed: ${s.length>40?s.slice(0,40)+"…":s}`:a?i?"Installing app…":c?`Install failed: ${c}`:null:"Starting device…":"Joining session…":"Connecting…"}function Pt(e){const{joined:t,fps:r,keyboardActive:s}=e,a=Ms(e),i=r>15,c=i?"#10b981":"#94a3b8",h=i?"Active":"Idle",d=o.useMemo(()=>Ts(),[]),m=Ls[d],[p,x]=o.useState(!1);o.useEffect(()=>{let b=!1;try{b=localStorage.getItem(Vt)==="1"}catch{}As(d,b)&&x(!0)},[d]);const u=b=>{if(x(b),!b)try{localStorage.setItem(Vt,"1")}catch{}};return n.jsxs("div",{className:"w-[300px] shrink-0 mt-3 rounded-xl border bg-background px-4 py-4 flex flex-col gap-3",children:[n.jsxs("div",{className:q("flex items-center",s?"text-emerald-500":"text-muted-foreground"),style:{gap:6},children:[n.jsx(Yr,{className:"h-3.5 w-3.5 shrink-0"}),n.jsx("span",{className:"text-[12px] font-medium",children:"Focus"})]}),t&&n.jsxs("div",{className:"flex items-center gap-[12px]",children:[n.jsxs("div",{className:"flex items-center gap-[4px]",children:[n.jsx("span",{className:"h-2 w-2 rounded-full shrink-0 mr-1",style:{background:c}}),n.jsx("span",{className:"text-[12px] font-mono text-foreground/75",children:r}),n.jsx("span",{className:"text-[12px] text-muted-foreground",children:"fps"}),n.jsx("span",{className:"text-[11px] text-muted-foreground/60",children:"·"}),n.jsx("span",{className:q("text-[11px]",i?"text-emerald-500":"text-muted-foreground/60"),children:h})]}),m&&n.jsxs(n.Fragment,{children:[n.jsx(tn,{orientation:"vertical",className:"h-3"}),d==="standard"?n.jsx("button",{type:"button",onClick:()=>x(!0),className:"text-[11px] text-foreground/70 hover:text-foreground underline-offset-2 hover:underline",children:m}):n.jsx("span",{className:"text-[11px] text-muted-foreground",children:m})]})]}),a&&n.jsx("p",{className:"text-[12px] text-muted-foreground leading-relaxed break-all",children:a}),n.jsx(Ds,{open:p,onOpenChange:u})]})}function gn({open:e,onOpenChange:t,sessionId:r,send:s}){const[a,i]=o.useState(""),c=o.useRef(null);o.useEffect(()=>{e?setTimeout(()=>{var d;return(d=c.current)==null?void 0:d.focus()},0):i("")},[e]);const h=()=>{a.trim()&&(s({type:"open-url",sessionId:r,payload:{url:a.trim()}}),t(!1))};return n.jsx(on,{open:e,onOpenChange:t,children:n.jsxs(an,{className:"w-[500px] max-w-[500px] h-[52px] !rounded-[18px] p-[10px] border border-border bg-background shadow-lg overflow-hidden [&>button]:hidden","aria-describedby":void 0,children:[n.jsx(cn,{className:"sr-only",children:"Open Deeplink"}),n.jsxs("div",{className:"flex items-center gap-3",children:[n.jsxs("div",{className:"flex-1 h-[32px] flex items-center gap-2 pl-[4px] pb-[1px]",children:[n.jsx(ar,{className:"h-4 w-4 text-muted-foreground shrink-0"}),n.jsx("input",{ref:c,className:"flex-1 bg-transparent text-sm outline-none placeholder:text-muted-foreground min-w-0",placeholder:"myapp://home...",value:a,onChange:d=>i(d.target.value),onKeyDown:d=>{d.key==="Enter"&&h()}})]}),n.jsx(ee,{size:"sm",disabled:!a.trim(),onClick:h,className:"shrink-0 rounded-xl h-8 px-4",children:"Open"})]})]})})}function Hs(e,t,r,s,a,i){const{x:c,y:h,width:d,height:m}=a;let p,x;if(i){const u=(e.x-t.left)/t.width;p=(1-(e.y-t.top)/t.height)*r,x=u*s}else p=(e.x-t.left)*(r/t.width),x=(e.y-t.top)*(s/t.height);return p<c||p>c+d||x<h||x>h+m?null:{x:(p-c)/d,y:(x-h)/m}}function Us(e,t,r){const s=(e.x-t.left)/t.width,a=(e.y-t.top)/t.height;return s<0||s>1||a<0||a>1?null:r?{x:a,y:1-s}:{x:s,y:a}}function xn(e){return{f0:{x:1-e.x,y:1-e.y},f1:e}}function Fs(e,t){return e>0?Math.min(1,t/e):1}const _t=22,Xt=[84,70,70,69],Is=1,$s=0,mt=1,bn=2,Bs=1,zs=2,Os=4;function Ws(e){if(e.byteLength<_t)return null;const t=new DataView(e);for(let a=0;a<Xt.length;a++)if(t.getUint8(a)!==Xt[a])return null;if(t.getUint8(4)!==Is)return null;const r=t.getUint8(5),s=r&Os?bn:r&Bs?mt:$s;return{capturedAt:Number(t.getBigUint64(6)),relayedAt:Number(t.getBigUint64(14)),codec:s,keyframe:s===mt&&(r&zs)!==0}}function yn(e){const{binaryFrameHandlerRef:t,perfHookRef:r,frameCount:s}=e,a=o.useRef(e);a.current=e,o.useEffect(()=>{let i=null,c=!1,h=!1,d;const m=()=>{if(i)return i;if(c)return null;const p=Ns();return p?(i=p,p.onResize(x=>a.current.onResize(x)),d=a.current.onDecoderReady(p),p):(c=!0,a.current.onUnsupported(),console.warn("[decoder] none available — set up HTTPS or use a supported browser"),null)};return t.current=(p,x)=>{const u=a.current.onJpegFrame;if(u&&(x==null?void 0:x.codec)!==mt){u(p,x);return}const b=m();if(b){if(!h){if(!(x!=null&&x.keyframe))return;h=!0}b.decode(p),s.current+=1}},()=>{t.current=void 0,typeof d=="function"&&d(),i==null||i.close(),i==null||i.surface.remove(),i=null}},[t,r,s])}const Ee=13,Ye=8,Yt=16,Vs=.02,Xs=100;function Ys({sessionId:e,buildId:t,send:r,connected:s,joined:a,deviceReady:i,installing:c,installed:h,installError:d,bootError:m,launching:p,setLaunching:x,chrome:u,binaryFrameHandlerRef:b,onRecordingUploaded:k,swKeyboardVisible:L,swKeyboardPending:C,onKbdToggle:N,perfHookRef:j}){const A=o.useRef(null),_=o.useRef(null),F=o.useRef(null),{fps:D,frameCount:B}=fn(),X=o.useRef(0),{recordState:I,recordCanvasRef:O,startClientRecording:Z,stopClientRecording:Re}=dn({sessionId:e,buildId:t,onRecordingUploaded:k}),fe=o.useRef(0),[ne,je]=o.useState(!1),[De,re]=o.useState(!1),[E,V]=o.useState(!1),[Y,ce]=o.useState(!1),[ke,se]=o.useState(null),[U,z]=o.useState(null),[le,Q]=o.useState(!1),[K,be]=o.useState(null),he=o.useRef(K);o.useEffect(()=>{he.current=K},[K]);const oe=o.useRef(null),ue=o.useRef(null),ae=o.useRef(!1),ie=o.useRef(!1),pe=o.useRef(0),te=o.useRef(null),me=o.useRef(null),Ce=o.useRef("idle"),_e=o.useRef(null),$e=o.useRef(null),Le=o.useRef(null);o.useEffect(()=>{Le.current=u},[u]),o.useEffect(()=>{const l=new Image;l.onload=()=>{$e.current=l},l.src=`data:image/png;base64,${u.framePng}`},[u.framePng]),yn({binaryFrameHandlerRef:b,perfHookRef:j,frameCount:B,onUnsupported:()=>{},onResize:l=>{const g=A.current;if(g&&(g.width!==l.width||g.height!==l.height)&&(g.width=l.width,g.height=l.height,!Le.current)){const f=O.current;f&&(f.width=l.width,f.height=l.height)}re(!0)},onDecoderReady:l=>{var y;const g=l.surface,f=A.current;g.style.position="absolute",f&&(g.style.left=f.style.left,g.style.top=f.style.top,g.style.width=f.style.width,g.style.height=f.style.height,g.style.borderRadius=f.style.borderRadius),g.style.objectFit="fill",g.style.zIndex="3",g.style.pointerEvents="none",(y=_.current)==null||y.appendChild(g);let S=null;const R=()=>{const P=A.current,M=P==null?void 0:P.getContext("2d");if(P&&M&&l.size)try{M.drawImage(l.surface,0,0,P.width,P.height)}catch{}S=requestAnimationFrame(R)};return S=requestAnimationFrame(R),()=>{S!==null&&cancelAnimationFrame(S)}},onJpegFrame:l=>{const g=performance.now();X.current&&g-X.current,X.current=g;const f=fe.current;createImageBitmap(new Blob([l],{type:"image/jpeg"})).then(S=>{if(performance.now()-g,fe.current!==f){S.close();return}const R=A.current,y=R==null?void 0:R.getContext("2d");if(!R||!y){S.close();return}if((R.width!==S.width||R.height!==S.height)&&(R.width=S.width,R.height=S.height,!Le.current)){const M=O.current;M&&(M.width=S.width,M.height=S.height)}const P=performance.now();y.drawImage(S,0,0),performance.now()-P,S.close(),re(!0),B.current+=1}).catch(()=>{})}}),o.useEffect(()=>{const l=O.current,g=_.current;l&&g&&(l.width=g.clientWidth,l.height=g.clientHeight)},[u]);const tt=o.useCallback(()=>{const l=O.current,g=A.current;if(!l||!g)return;const f=l.getContext("2d");if(!f)return;const S=Le.current;if(f.clearRect(0,0,l.width,l.height),S){$e.current&&f.drawImage($e.current,0,0,l.width,l.height);const P=Math.round(S.screenCornerRadius/2*(l.height/(S.compositeHeight/2)));f.save(),f.beginPath(),P>0?f.roundRect(g.offsetLeft,g.offsetTop,g.clientWidth,g.clientHeight,P):f.rect(g.offsetLeft,g.offsetTop,g.clientWidth,g.clientHeight),f.clip(),f.drawImage(g,g.offsetLeft,g.offsetTop,g.clientWidth,g.clientHeight),f.restore()}else f.drawImage(g,0,0,l.width,l.height);const R=he.current;if(R)for(const P of[R.f0,R.f1]){const M=S?g.offsetLeft+P.x*g.clientWidth:P.x*l.width,W=S?g.offsetTop+P.y*g.clientHeight:P.y*l.height;ae.current?(f.beginPath(),f.arc(M,W,Ye,0,Math.PI*2),f.fillStyle="rgba(255,255,255,0.92)",f.fill(),f.strokeStyle="rgba(0,0,0,0.2)",f.lineWidth=1,f.stroke()):(f.beginPath(),f.arc(M,W,Ee,0,Math.PI*2),f.strokeStyle="rgba(0,0,0,0.3)",f.lineWidth=3,f.stroke(),f.beginPath(),f.arc(M,W,Ee,0,Math.PI*2),f.strokeStyle="rgba(255,255,255,0.65)",f.lineWidth=1.5,f.stroke())}const y=me.current;if(y){const P=Ce.current,M=_e.current;if(f.save(),P==="down")f.beginPath(),f.arc(y.x,y.y,Ye,0,Math.PI*2),f.fillStyle="rgba(255,255,255,0.92)",f.fill(),f.strokeStyle="rgba(0,0,0,0.2)",f.lineWidth=1,f.stroke();else if(P==="release"&&M){const W=Math.min((performance.now()-M.startTime)/350,1);f.beginPath(),f.arc(y.x,y.y,Ye+26*W,0,Math.PI*2),f.strokeStyle=`rgba(255,255,255,${(1-W)*.55})`,f.lineWidth=1.5,f.stroke(),W>=1&&(Ce.current="idle",_e.current=null)}else f.beginPath(),f.arc(y.x,y.y,Ee,0,Math.PI*2),f.strokeStyle="rgba(0,0,0,0.3)",f.lineWidth=3,f.stroke(),f.beginPath(),f.arc(y.x,y.y,Ee,0,Math.PI*2),f.strokeStyle="rgba(255,255,255,0.65)",f.lineWidth=1.5,f.stroke();f.restore()}},[]),Be=o.useCallback(()=>{const l=A.current;if(!l)return;const g=document.createElement("canvas"),f=g.getContext("2d");f&&(g.width=l.width,g.height=l.height,f.drawImage(l,0,0),g.toBlob(S=>{if(!S)return;const R=URL.createObjectURL(S),y=document.createElement("a");y.href=R,y.download=`tapflow-${Date.now()}.png`,y.click(),URL.revokeObjectURL(R)},"image/png"))},[]),ye=o.useCallback(()=>{if(I==="idle"){const l=O.current;if(!l)return;const g=_.current;if(g&&g.clientWidth>0)l.width=g.clientWidth,l.height=g.clientHeight;else{const f=A.current;if(f&&f.width>0)l.width=f.width,l.height=f.height;else return}Z(tt)}else I==="recording"&&Re()},[I,Z,Re,tt]),Te=o.useCallback(()=>{r({type:"input:rotate",sessionId:e}),V(l=>!l)},[r,e]),it=o.useRef(E);o.useEffect(()=>{it.current=E},[E]),o.useEffect(()=>()=>{it.current&&r({type:"input:rotate",sessionId:e})},[]),o.useEffect(()=>{const l=new Set(["ShiftLeft","ShiftRight","ControlLeft","ControlRight","MetaLeft","MetaRight"]),g=y=>{if(y.code==="AltLeft"||y.code==="AltRight"){ie.current=!0;return}if(y.metaKey){const M=document.activeElement;if(!M||M.tagName!=="INPUT"&&M.tagName!=="TEXTAREA"){if(!y.shiftKey&&y.code==="KeyK"){y.preventDefault(),je(!0);return}if(!y.shiftKey&&y.code==="KeyS"){y.preventDefault(),Be();return}if(y.shiftKey&&y.code==="KeyY"){y.preventDefault(),ye();return}if(y.shiftKey&&y.code==="KeyO"){y.preventDefault(),Te();return}if(y.shiftKey&&y.code==="KeyU"){y.preventDefault(),r({type:"input:button",sessionId:e,payload:{name:"home"}});return}if(y.shiftKey&&y.code==="KeyK"){y.preventDefault(),C||N();return}}}if(!Y||l.has(y.code))return;y.preventDefault();const P=(y.shiftKey?2:0)|(y.ctrlKey?1:0)|(y.metaKey?8:0);r({type:"input:key",sessionId:e,payload:{code:y.code,modifiers:P}})},f=()=>{ae.current&&(ae.current=!1,Q(!1),r({type:"input:pinch:end",sessionId:e})),ie.current=!1,be(null)},S=y=>{(y.code==="AltLeft"||y.code==="AltRight")&&f()},R=()=>{ie.current&&f()};return window.addEventListener("keydown",g),window.addEventListener("keyup",S),window.addEventListener("blur",R),()=>{window.removeEventListener("keydown",g),window.removeEventListener("keyup",S),window.removeEventListener("blur",R)}},[Y,r,e,Be,ye,Te,N,C]),o.useEffect(()=>{if(!Y)return;const l=g=>{const f=_.current??A.current;f&&!f.contains(g.target)&&ce(!1)};return document.addEventListener("pointerdown",l),()=>document.removeEventListener("pointerdown",l)},[Y]);const Pe=o.useCallback(l=>{const g=(E?F.current:null)??_.current;if(!g)return null;const f=g.getBoundingClientRect(),S=u.compositeWidth/2,R=u.compositeHeight/2,y=u.screenRect.x/2,P=u.screenRect.y/2,M=u.screenRect.width/2,W=u.screenRect.height/2;return Hs({x:l.clientX,y:l.clientY},f,S,R,{x:y,y:P,width:M,height:W},E)},[u,E]),ze=o.useCallback(l=>{const g=Pe(l);return g?xn(g):null},[Pe]),Je=o.useCallback(l=>{const g=E?F.current:_.current;if(!g)return null;const f=g.getBoundingClientRect();let S,R;if(E){const P=f.height-(l.clientY-f.top),M=l.clientX-f.left;S=P*(u.compositeWidth/f.height),R=M*(u.compositeHeight/f.width)}else S=(l.clientX-f.left)*(u.compositeWidth/f.width),R=(l.clientY-f.top)*(u.compositeHeight/f.height);const y=u.screenRect;if(S>=y.x&&S<=y.x+y.width&&R>=y.y&&R<=y.y+y.height)return null;for(const P of u.buttons){const M=S-P.normalOffset.x,W=R-P.normalOffset.y;if(M*M+W*W<Xs**2)return P.name}return null},[u,E]),Oe=o.useCallback(l=>{const g=A.current,f=O.current;return g&&g.clientWidth>0?{x:g.offsetLeft+l.x*g.clientWidth,y:g.offsetTop+l.y*g.clientHeight}:{x:l.x*((f==null?void 0:f.width)??1),y:l.y*((f==null?void 0:f.height)??1)}},[]),ge=o.useCallback(l=>{if(ce(!0),ie.current){const y=ze(l);if(!y)return;ae.current=!0,Q(!0),l.target.setPointerCapture(l.pointerId),be(y),r({type:"input:pinch:start",sessionId:e,payload:y});return}const g=Je(l);if(g){oe.current=g,se(g),l.target.setPointerCapture(l.pointerId),r({type:"input:button",sessionId:e,payload:{name:g,phase:"down"}});return}const f=Pe(l);if(!f)return;ue.current=f,l.target.setPointerCapture(l.pointerId),me.current=Oe(f),Ce.current="down",_e.current=null;const S=l.currentTarget.getBoundingClientRect(),R=te.current;R&&(R.style.display="block",R.style.left=`${l.clientX-S.left}px`,R.style.top=`${l.clientY-S.top}px`,R.style.width=`${Ye*2}px`,R.style.height=`${Ye*2}px`,R.style.background="rgba(255,255,255,0.92)",R.style.border="1.5px solid rgba(0,0,0,0.2)",R.style.boxShadow="0 0 0 1px rgba(0,0,0,0.15), 0 0 8px rgba(255,255,255,0.25)"),r({type:"input:touch:start",sessionId:e,payload:f})},[Je,Pe,ze,Oe,r,e]),ct=o.useCallback(l=>{if(l.buttons===0){if(z(Je(l)),ie.current){be(ze(l)),me.current=null;const P=te.current;P&&(P.style.display="none")}else{be(null);const P=Pe(l);me.current=P?Oe(P):null,Ce.current!=="down"&&(Ce.current="idle");const M=te.current;if(M)if(P){const W=l.currentTarget.getBoundingClientRect();M.style.display="block",M.style.left=`${l.clientX-W.left}px`,M.style.top=`${l.clientY-W.top}px`,M.style.width=`${Ee*2}px`,M.style.height=`${Ee*2}px`,M.style.background="transparent",M.style.border="1.5px solid rgba(255,255,255,0.6)",M.style.boxShadow="0 0 0 1px rgba(0,0,0,0.3)"}else M.style.display="none"}return}if(ae.current){const P=ze(l);if(!P)return;const M=performance.now();if(M-pe.current<Yt)return;pe.current=M,be(P),r({type:"input:pinch:move",sessionId:e,payload:P});return}if(oe.current||!ue.current)return;const g=Pe(l);if(!g)return;const f=g.x-ue.current.x,S=g.y-ue.current.y;if(Math.sqrt(f*f+S*S)<Vs)return;const R=performance.now();if(R-pe.current<Yt)return;pe.current=R,me.current=Oe(g);const y=te.current;if(y&&y.style.display!=="none"){const P=l.currentTarget.getBoundingClientRect();y.style.left=`${l.clientX-P.left}px`,y.style.top=`${l.clientY-P.top}px`}r({type:"input:touch:move",sessionId:e,payload:g})},[Je,Pe,ze,Oe,r,e]),Me=o.useCallback(()=>{if(ae.current){ae.current=!1,Q(!1),be(null),r({type:"input:pinch:end",sessionId:e});return}if(ue.current=null,oe.current){r({type:"input:button",sessionId:e,payload:{name:oe.current,phase:"up"}}),oe.current=null,setTimeout(()=>se(null),100);return}Ce.current="release",_e.current={startTime:performance.now()};const l=te.current;l&&(l.style.width=`${Ee*2}px`,l.style.height=`${Ee*2}px`,l.style.background="transparent",l.style.border="1.5px solid rgba(255,255,255,0.6)",l.style.boxShadow="0 0 0 1px rgba(0,0,0,0.3)"),r({type:"input:touch:end",sessionId:e})},[r,e]),We=o.useCallback(()=>{if(ae.current){ae.current=!1,Q(!1),be(null),r({type:"input:pinch:end",sessionId:e});return}if(ue.current=null,oe.current){r({type:"input:button",sessionId:e,payload:{name:oe.current,phase:"up"}}),oe.current=null,se(null);return}Ce.current="release",_e.current={startTime:performance.now()},r({type:"input:touch:end",sessionId:e})},[r,e]),St=o.useCallback(()=>{z(null),be(null),me.current=null;const l=te.current;l&&(l.style.display="none")},[]),He=u.compositeWidth/2,lt=u.compositeHeight/2,Ze=Fs(lt,750),Ve=Math.round(He*Ze),Xe=Math.round(lt*Ze),Qe=u.screenRect.x/u.compositeWidth*100,v=u.screenRect.y/u.compositeHeight*100,T=u.screenRect.width/u.compositeWidth*100,$=u.screenRect.height/u.compositeHeight*100,w=Math.round(u.screenCornerRadius/2*Ze),G=n.jsxs(n.Fragment,{children:[n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:()=>r({type:"input:button",sessionId:e,payload:{name:"home"}}),children:n.jsx(ln,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsxs("span",{className:"flex items-center gap-3",children:["Home ",n.jsxs(Et,{children:[n.jsx(Ge,{children:"⌘"}),n.jsx(Ge,{children:"⇧"}),n.jsx(Ge,{children:"U"})]})]})})]}),n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",disabled:C,onClick:N,"data-active":L,children:C?n.jsx(pt,{className:"h-4 w-4 animate-spin"}):n.jsx(Ur,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:n.jsxs("span",{className:"flex items-center gap-3",children:["Software keyboard ",n.jsxs(Et,{children:[n.jsx(Ge,{children:"⌘"}),n.jsx(Ge,{children:"⇧"}),n.jsx(Ge,{children:"K"})]})]})})]})]}),H=h&&t?n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",disabled:p,onClick:()=>{x(!0),r({type:"app:launch",sessionId:e,buildId:t})},children:p?n.jsx(pt,{className:"h-4 w-4 animate-spin"}):n.jsx(rn,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:p?"Launching…":"Launch app"})]}):null;return n.jsxs("div",{className:"flex items-start justify-center gap-16",children:[n.jsx("canvas",{ref:O,style:{display:"none"}}),n.jsx(gn,{open:ne,onOpenChange:je,sessionId:e,send:r}),n.jsx(hn,{joined:a,onDeepLink:()=>je(!0),onScreenshot:Be,onRecordToggle:ye,recordState:I,onRotate:Te,platformSlot:G,launchSlot:H}),n.jsxs("div",{className:"flex items-start gap-8",children:[n.jsxs("div",{ref:F,style:{width:E?Xe:Ve,height:E?Ve:Xe,position:"relative",flexShrink:0},children:[n.jsxs("div",{ref:_,className:`relative ${U?"cursor-pointer":"cursor-default"}`,style:{width:Ve,height:Xe,...E?{position:"absolute",top:(Ve-Xe)/2,left:(Xe-Ve)/2,transform:"rotate(-90deg)",transformOrigin:"center center"}:{}},onPointerDown:ge,onPointerMove:ct,onPointerUp:Me,onPointerCancel:We,onPointerLeave:St,children:[n.jsx("img",{src:`data:image/png;base64,${u.framePng}`,style:{position:"absolute",top:0,left:0,zIndex:2,width:"100%",height:"100%",display:"block",pointerEvents:"none",userSelect:"none"},draggable:!1,alt:""}),n.jsx("canvas",{ref:A,style:{position:"absolute",zIndex:3,left:`${Qe}%`,top:`${v}%`,width:`${T}%`,height:`${$}%`,borderRadius:w>0?`${w}px`:void 0,backgroundColor:"#010101",cursor:"none",visibility:De?"visible":"hidden"}}),!De&&n.jsx("div",{className:"absolute animate-pulse bg-zinc-700",style:{zIndex:3,left:`${Qe}%`,top:`${v}%`,width:`${T}%`,height:`${$}%`,borderRadius:w>0?`${w}px`:void 0}}),K&&(()=>{const l=Qe/100,g=v/100,f=T/100,S=$/100,R=(y,P)=>({left:`${(l+y*f)*100}%`,top:`${(g+P*S)*100}%`});return n.jsx(n.Fragment,{children:[K.f0,K.f1].map((y,P)=>n.jsx("div",{style:{position:"absolute",zIndex:10,borderRadius:"50%",transform:"translate(-50%, -50%)",pointerEvents:"none",transition:"width 0.1s ease, height 0.1s ease, background 0.1s ease",...le?{width:Ye*2,height:Ye*2,background:"rgba(255,255,255,0.92)",border:"1.5px solid rgba(0,0,0,0.2)",boxShadow:"0 0 0 1px rgba(0,0,0,0.15), 0 0 8px rgba(255,255,255,0.25)"}:{width:Ee*2,height:Ee*2,background:"transparent",border:"1.5px solid rgba(255,255,255,0.6)",boxShadow:"0 0 0 1px rgba(0,0,0,0.3)"},...R(y.x,y.y)}},P))})})(),a&&D===0&&n.jsx("div",{style:{position:"absolute",zIndex:8,left:`${Qe}%`,top:`${v}%`,width:`${T}%`,height:`${$}%`,display:"flex",alignItems:"center",justifyContent:"center",pointerEvents:"none"},children:n.jsx("span",{style:{color:"white",fontSize:"0.875rem"},children:"Waiting for first frame..."})}),u.buttons.map(l=>{const g=ke===l.name,f=U===l.name,S=l.anchor==="bottom",R=l.anchor==="top",y=S?(l.normalOffset.y-l.buttonH/2)/u.compositeHeight*100:R?l.rolloverOffset.y/u.compositeHeight*100:(l.normalOffset.y-l.buttonH/2)/u.compositeHeight*100,P=l.buttonH/u.compositeHeight*100,M=l.buttonW/u.compositeWidth*100,W=l.buttonW/2,de=(l.rolloverOffset.x-W)/u.compositeWidth*100,Ae=(2*l.rolloverOffset.x-l.normalOffset.x-W)/u.compositeWidth*100,ut=l.rolloverOffset.x/u.compositeWidth*100,nt=S?(l.normalOffset.y-l.buttonH/2)/u.compositeHeight*100:R?l.rolloverOffset.y/u.compositeHeight*100:(l.normalOffset.y-l.buttonH/2)/u.compositeHeight*100,It=R?(2*l.rolloverOffset.y-l.normalOffset.y)/u.compositeHeight*100:0,Yn=l.onTop?4:1;return n.jsxs(o.Fragment,{children:[l.buttonPng&&n.jsx("img",{src:`data:image/png;base64,${l.buttonPng}`,style:{position:"absolute",zIndex:Yn,top:`${R&&f?It:y}%`,left:`${R?de:f?Ae:de}%`,width:`${M}%`,height:`${P}%`,transition:R?"top 0.15s ease":"left 0.15s ease",pointerEvents:"none",userSelect:"none"},draggable:!1,alt:""}),g&&l.pressedPng&&l.pressedRect&&n.jsx("img",{src:`data:image/png;base64,${l.pressedPng}`,style:{position:"absolute",zIndex:l.onTop?3:1,left:`${R?de:f?Ae:de}%`,top:`${R&&f?It:y}%`,width:`${l.pressedRect.width/u.compositeWidth*100}%`,height:`${l.pressedRect.height/u.compositeHeight*100}%`,pointerEvents:"none",userSelect:"none"},draggable:!1,alt:""}),f&&n.jsx("div",{className:"bg-foreground/85 text-background text-[11px] px-[7px] py-1.5 rounded-lg whitespace-nowrap pointer-events-none",style:{position:"absolute",zIndex:5,left:`${ut}%`,top:`${nt}%`,transform:"translate(-50%, calc(-100% - 8px))"},children:l.accessibilityTitle})]},l.name)})]}),n.jsx("div",{ref:te,style:{display:"none",position:"absolute",zIndex:20,borderRadius:"50%",transform:"translate(-50%, -50%)",pointerEvents:"none",transition:"width 0.1s ease, height 0.1s ease, background 0.1s ease, box-shadow 0.1s ease"}})]}),n.jsx(Pt,{joined:a,fps:D,connected:s,deviceReady:i,bootError:m,installing:c,installError:d,keyboardActive:Y})]})]})}const Ke=13,st=8,Kt=16,Ks=.02,jt=720;function Gs({sessionId:e,buildId:t,send:r,connected:s,joined:a,deviceReady:i,installing:c,installed:h,installError:d,bootError:m,launching:p,setLaunching:x,androidButtons:u,binaryFrameHandlerRef:b,onRecordingUploaded:k,screenWidth:L,screenHeight:C,cornerRadius:N,perfHookRef:j}){const A=o.useRef(null),_=o.useRef(null),F=o.useRef(null),{fps:D,frameCount:B}=fn(),{recordState:X,recordCanvasRef:I,startClientRecording:O,stopClientRecording:Z}=dn({sessionId:e,buildId:t,onRecordingUploaded:k}),[Re,fe]=o.useState(!1),[ne,je]=o.useState(!1),[De,re]=o.useState(!1),E=o.useRef(null),[V,Y]=o.useState(null),[ce,ke]=o.useState(!1),[se,U]=o.useState(!1),[z,le]=o.useState(!1),[Q,K]=o.useState(null),be=o.useRef(Q);o.useEffect(()=>{be.current=Q},[Q]);const he=o.useRef(!1),oe=o.useRef(!1),ue=o.useRef(null),ae=o.useRef(0),ie=o.useRef(null),pe=o.useRef(null),te=o.useRef("idle"),me=o.useRef(null);yn({binaryFrameHandlerRef:b,perfHookRef:j,frameCount:B,onUnsupported:()=>re(!0),onResize:v=>{je(!0);const T=E.current;(!T||T.width!==v.width||T.height!==v.height)&&(E.current=v,Y(v))},onDecoderReady:v=>{var $;F.current=v;const T=v.surface;T.style.display="block",T.style.width="100%",T.style.height="100%",T.style.objectFit="fill",($=A.current)==null||$.appendChild(T)}});const Ce=o.useCallback(()=>{var M;const v=I.current,T=(M=F.current)==null?void 0:M.surface,$=E.current;if(!v||!T||!$)return;const w=v.getContext("2d");if(!w)return;const G=$.width,H=$.height,l=v.width>v.height!=G>H;w.save(),l&&(w.translate(v.width,0),w.rotate(Math.PI/2)),w.drawImage(T,0,0,G,H);const g=Math.max(G,H),f=g>jt?g/jt:1,S=Ke*f,R=st*f,y=be.current;if(y)for(const W of[y.f0,y.f1]){const de=W.x*G,Ae=W.y*H;he.current?(w.beginPath(),w.arc(de,Ae,R,0,Math.PI*2),w.fillStyle="rgba(255,255,255,0.92)",w.fill(),w.strokeStyle="rgba(0,0,0,0.2)",w.lineWidth=f,w.stroke()):(w.beginPath(),w.arc(de,Ae,S,0,Math.PI*2),w.strokeStyle="rgba(0,0,0,0.3)",w.lineWidth=3*f,w.stroke(),w.beginPath(),w.arc(de,Ae,S,0,Math.PI*2),w.strokeStyle="rgba(255,255,255,0.65)",w.lineWidth=1.5*f,w.stroke())}const P=pe.current;if(P){const W=P.x*G,de=P.y*H,Ae=te.current,ut=me.current;if(Ae==="down")w.beginPath(),w.arc(W,de,R,0,Math.PI*2),w.fillStyle="rgba(255,255,255,0.92)",w.fill(),w.strokeStyle="rgba(0,0,0,0.2)",w.lineWidth=f,w.stroke();else if(Ae==="release"&&ut){const nt=Math.min((performance.now()-ut.startTime)/350,1);w.beginPath(),w.arc(W,de,R+26*f*nt,0,Math.PI*2),w.strokeStyle=`rgba(255,255,255,${(1-nt)*.55})`,w.lineWidth=1.5*f,w.stroke(),nt>=1&&(te.current="idle",me.current=null)}else w.beginPath(),w.arc(W,de,S,0,Math.PI*2),w.strokeStyle="rgba(0,0,0,0.3)",w.lineWidth=3*f,w.stroke(),w.beginPath(),w.arc(W,de,S,0,Math.PI*2),w.strokeStyle="rgba(255,255,255,0.65)",w.lineWidth=1.5*f,w.stroke()}w.restore()},[]),_e=o.useCallback(()=>{var G;const v=(G=F.current)==null?void 0:G.surface,T=E.current;if(!v||!T)return;const $=document.createElement("canvas"),w=$.getContext("2d");w&&($.width=T.width,$.height=T.height,w.drawImage(v,0,0,T.width,T.height),$.toBlob(H=>{if(!H)return;const l=URL.createObjectURL(H),g=document.createElement("a");g.href=l,g.download=`tapflow-${Date.now()}.png`,g.click(),URL.revokeObjectURL(l)},"image/png"))},[]),$e=o.useCallback(()=>{if(X==="idle"){const v=I.current;if(!v)return;const T=E.current;if(!T)return;const $=Be.current;v.width=$?T.height:T.width,v.height=$?T.width:T.height,O(Ce)}else X==="recording"&&Z()},[X,O,Z,Ce]),Le=o.useCallback(()=>{r({type:"input:rotate",sessionId:e}),ke(v=>!v)},[r,e]),tt=o.useRef(ce);o.useEffect(()=>{tt.current=ce},[ce]),o.useEffect(()=>()=>{tt.current&&r({type:"input:rotate",sessionId:e})},[]),o.useEffect(()=>{const v=new Set(["ShiftLeft","ShiftRight","ControlLeft","ControlRight","MetaLeft","MetaRight"]),T=H=>{if(H.code==="AltLeft"||H.code==="AltRight"){oe.current=!0;return}if(H.metaKey){const g=document.activeElement;if(!g||g.tagName!=="INPUT"&&g.tagName!=="TEXTAREA"){if(!H.shiftKey&&H.code==="KeyK"){H.preventDefault(),fe(!0);return}if(!H.shiftKey&&H.code==="KeyS"){H.preventDefault(),_e();return}if(H.shiftKey&&H.code==="KeyY"){H.preventDefault(),$e();return}if(H.shiftKey&&H.code==="KeyO"){H.preventDefault(),Le();return}}}if(!se||v.has(H.code))return;H.preventDefault();const l=(H.shiftKey?2:0)|(H.ctrlKey?1:0)|(H.metaKey?8:0);r({type:"input:key",sessionId:e,payload:{code:H.code,modifiers:l}})},$=()=>{he.current&&(he.current=!1,le(!1),r({type:"input:pinch:end",sessionId:e})),oe.current=!1,K(null)},w=H=>{(H.code==="AltLeft"||H.code==="AltRight")&&$()},G=()=>{oe.current&&$()};return window.addEventListener("keydown",T),window.addEventListener("keyup",w),window.addEventListener("blur",G),()=>{window.removeEventListener("keydown",T),window.removeEventListener("keyup",w),window.removeEventListener("blur",G)}},[se,r,e,_e,$e,Le]),o.useEffect(()=>{if(!se)return;const v=T=>{const $=_.current??A.current;$&&!$.contains(T.target)&&U(!1)};return document.addEventListener("pointerdown",v),()=>document.removeEventListener("pointerdown",v)},[se]);const Be=o.useRef(!1),ye=o.useCallback(v=>{const T=A.current;if(!T)return null;const $=T.getBoundingClientRect();return Us({x:v.clientX,y:v.clientY},$,Be.current)},[]),Te=o.useCallback(v=>{const T=ye(v);return T?xn(T):null},[ye]),it=o.useCallback(v=>{if(oe.current){const G=Te(v);if(!G)return;he.current=!0,le(!0),v.target.setPointerCapture(v.pointerId);const H=ie.current;H&&(H.style.display="none"),K(G),r({type:"input:pinch:start",sessionId:e,payload:G});return}const T=ye(v);if(!T)return;U(!0),ue.current=T,v.target.setPointerCapture(v.pointerId);const $=v.currentTarget.getBoundingClientRect();pe.current=T,te.current="down",me.current=null;const w=ie.current;w&&(w.style.display="block",w.style.left=`${v.clientX-$.left}px`,w.style.top=`${v.clientY-$.top}px`,w.style.width=`${st*2}px`,w.style.height=`${st*2}px`,w.style.background="rgba(255,255,255,0.92)",w.style.border="1.5px solid rgba(0,0,0,0.2)",w.style.boxShadow="0 0 0 1px rgba(0,0,0,0.15), 0 0 8px rgba(255,255,255,0.25)"),r({type:"input:touch:start",sessionId:e,payload:T})},[ye,Te,r,e]),Pe=o.useCallback(v=>{if(v.buttons===0){if(oe.current){K(Te(v)),pe.current=null;const R=ie.current;R&&(R.style.display="none");return}const g=ye(v),f=v.currentTarget.getBoundingClientRect(),S=ie.current;g?(pe.current=g,te.current!=="down"&&(te.current="idle"),S&&(S.style.display="block",S.style.left=`${v.clientX-f.left}px`,S.style.top=`${v.clientY-f.top}px`,S.style.width=`${Ke*2}px`,S.style.height=`${Ke*2}px`,S.style.background="transparent",S.style.border="1.5px solid rgba(255,255,255,0.6)",S.style.boxShadow="0 0 0 1px rgba(0,0,0,0.3)")):(pe.current=null,S&&(S.style.display="none"));return}if(he.current){const g=Te(v);if(!g)return;const f=performance.now();if(f-ae.current<Kt)return;ae.current=f,K(g),r({type:"input:pinch:move",sessionId:e,payload:g});return}if(!ue.current)return;const T=ye(v);if(!T)return;const $=T.x-ue.current.x,w=T.y-ue.current.y;if(Math.sqrt($*$+w*w)<Ks)return;const G=performance.now();if(G-ae.current<Kt)return;ae.current=G;const H=v.currentTarget.getBoundingClientRect();pe.current=T;const l=ie.current;l&&l.style.display!=="none"&&(l.style.left=`${v.clientX-H.left}px`,l.style.top=`${v.clientY-H.top}px`),r({type:"input:touch:move",sessionId:e,payload:T})},[ye,Te,r,e]),ze=o.useCallback(()=>{if(he.current){he.current=!1,le(!1),K(null),r({type:"input:pinch:end",sessionId:e});return}ue.current=null,te.current="release",me.current={startTime:performance.now()};const v=ie.current;v&&(v.style.width=`${Ke*2}px`,v.style.height=`${Ke*2}px`,v.style.background="transparent",v.style.border="1.5px solid rgba(255,255,255,0.6)",v.style.boxShadow="0 0 0 1px rgba(0,0,0,0.3)"),r({type:"input:touch:end",sessionId:e})},[r,e]),Je=o.useCallback(()=>{if(he.current){he.current=!1,le(!1),K(null),r({type:"input:pinch:end",sessionId:e});return}ue.current=null,te.current="release",me.current={startTime:performance.now()},r({type:"input:touch:end",sessionId:e})},[r,e]),Oe=o.useCallback(()=>{K(null),pe.current=null;const v=ie.current;v&&(v.style.display="none")},[]),ge=V??(L&&C?{width:L,height:C}:null),ct=ge?Math.min(1,jt/Math.max(ge.width,ge.height)):.3,Me=ge?Math.round(ge.width*ct):324,We=ge?Math.round(ge.height*ct):720,St=ge?ge.width>ge.height:!1,He=ce&&!St;o.useLayoutEffect(()=>{Be.current=He},[He]);const lt=He?We:Me,Ft=He?Me:We,Ze=N!=null?Math.round(N*Me):22,Ve=He?{position:"absolute",width:Me,height:We,top:(Me-We)/2,left:(We-Me)/2,transform:"rotate(90deg)",transformOrigin:"center center",visibility:ne?"visible":"hidden",cursor:"none"}:{visibility:ne?"visible":"hidden",cursor:"none"},Xe=n.jsx(n.Fragment,{children:u==null?void 0:u.map(v=>n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",onClick:()=>r({type:"input:button",sessionId:e,payload:{name:v.name}}),children:v.name==="back"?n.jsx(Sr,{className:"h-4 w-4"}):v.name==="recent_apps"?n.jsx(Kn,{className:"h-4 w-4"}):v.name==="volume_up"?n.jsx(Qr,{className:"h-4 w-4"}):v.name==="volume_down"?n.jsx(ts,{className:"h-4 w-4"}):v.name==="power"?n.jsx(Or,{className:"h-4 w-4"}):n.jsx(ln,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:v.accessibilityTitle})]},v.name))}),Qe=h&&t?n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx(ee,{variant:"ghost",size:"icon",className:"h-8 w-8",disabled:p||c,onClick:()=>{x(!0),r({type:"app:launch",sessionId:e,buildId:t})},children:p?n.jsx(pt,{className:"h-4 w-4 animate-spin"}):n.jsx(rn,{className:"h-4 w-4"})})}),n.jsx(Se,{side:"left",children:p?"Launching…":c?"Installing…":"Launch app"})]}):null;return n.jsxs("div",{className:"flex items-start justify-center gap-16",children:[n.jsx("canvas",{ref:I,style:{display:"none"}}),n.jsx(gn,{open:Re,onOpenChange:fe,sessionId:e,send:r}),n.jsx(hn,{joined:a,onDeepLink:()=>fe(!0),onScreenshot:_e,onRecordToggle:$e,recordState:X,onRotate:Le,platformSlot:Xe,launchSlot:Qe}),n.jsxs("div",{className:"flex items-start gap-8",children:[n.jsx("div",{style:{background:"#1c1c1e",borderRadius:`${Ze+12}px`,padding:"12px",flexShrink:0,boxShadow:"0 8px 32px rgba(0,0,0,0.45), inset 0 1px 0 rgba(255,255,255,0.06)"},children:n.jsx("div",{ref:_,className:"relative",style:{width:lt,height:Ft,backgroundColor:"#010101",borderRadius:`${Ze}px`,overflow:"hidden"},children:De?n.jsx("div",{className:"absolute inset-0 flex items-center justify-center p-4 text-center",children:n.jsxs("span",{style:{color:"rgba(255,255,255,0.6)",fontSize:"0.875rem"},children:["이 환경에서는 스트리밍을 표시할 수 없습니다.",n.jsx("br",{}),"Chrome/Edge 또는 HTTPS 환경에서 다시 시도해 주세요."]})}):n.jsxs(n.Fragment,{children:[n.jsx("div",{ref:A,className:He?void 0:"block w-full h-full",style:Ve,onPointerDown:it,onPointerMove:Pe,onPointerUp:ze,onPointerCancel:Je,onPointerLeave:Oe}),!ne&&n.jsx("div",{className:"absolute inset-0 animate-pulse bg-zinc-700"}),!ne&&i&&n.jsx("div",{className:"absolute inset-0 flex items-center justify-center pointer-events-none",children:n.jsx("span",{style:{color:"rgba(255,255,255,0.6)",fontSize:"0.875rem"},children:"Waiting for stream…"})}),n.jsx("div",{ref:ie,style:{display:"none",position:"absolute",zIndex:20,borderRadius:"50%",transform:"translate(-50%, -50%)",pointerEvents:"none",transition:"width 0.1s ease, height 0.1s ease, background 0.1s ease, box-shadow 0.1s ease"}}),Q&&n.jsx(n.Fragment,{children:[Q.f0,Q.f1].map((v,T)=>n.jsx("div",{style:{position:"absolute",zIndex:10,borderRadius:"50%",transform:"translate(-50%, -50%)",pointerEvents:"none",transition:"width 0.1s ease, height 0.1s ease, background 0.1s ease",left:`${v.x*100}%`,top:`${v.y*100}%`,...z?{width:st*2,height:st*2,background:"rgba(255,255,255,0.92)",border:"1.5px solid rgba(0,0,0,0.2)",boxShadow:"0 0 0 1px rgba(0,0,0,0.15), 0 0 8px rgba(255,255,255,0.25)"}:{width:Ke*2,height:Ke*2,background:"transparent",border:"1.5px solid rgba(255,255,255,0.6)",boxShadow:"0 0 0 1px rgba(0,0,0,0.3)"}}},T))})]})})}),n.jsx(Pt,{joined:a,fps:D,connected:s,deviceReady:i,bootError:m,installing:c,installError:d,keyboardActive:se})]})]})}function qs(e,t){const r=new DataView(e),s=Math.floor(e.byteLength/2),a=Math.floor(s/t),i=[];for(let c=0;c<t;c++)i.push(new Float32Array(a));for(let c=0;c<a;c++)for(let h=0;h<t;h++){const d=r.getInt16((c*t+h)*2,!0);i[h][c]=d/32768}return i}const Js=44100,kt=2,Gt=.06,Zs=.3;function Qs(){const e=o.useRef(null),t=o.useRef(0),r=o.useCallback(()=>{if(e.current)return e.current;const a=window.AudioContext??window.webkitAudioContext;return a?(e.current=new a,e.current):null},[]),s=o.useCallback(a=>{var u;const i=r();if(!i)return;i.state==="suspended"&&i.resume();const c=qs(a,kt),h=((u=c[0])==null?void 0:u.length)??0;if(h===0)return;const d=i.createBuffer(kt,h,Js);for(let b=0;b<kt;b++)d.getChannelData(b).set(c[b]);const m=i.createBufferSource();m.buffer=d,m.connect(i.destination);const p=i.currentTime;let x=t.current;(x<p+.005||x>p+Zs+Gt)&&(x=p+Gt),m.start(x),t.current=x+d.duration},[r]);return o.useEffect(()=>()=>{var a;(a=e.current)==null||a.close(),e.current=null},[]),{pushFrame:s}}function eo({sessionId:e,deviceId:t,buildId:r,resetMode:s,onRecordingUploaded:a}){const i=o.useRef(()=>{});os();const c=o.useRef(null),h=o.useRef(null),d=o.useRef([]);o.useRef({onFrameBegin:()=>{var U;return(U=c.current)==null?void 0:U.onFrameBegin()},onFrameEnd:U=>{var Q,K;const z=d.current.shift()??null,le=z?{...U,capturedAt:z.capturedAt,relayedAt:z.relayedAt}:U;(Q=c.current)==null||Q.onFrameEnd(le),(K=h.current)==null||K.call(h,le)}});const[m,p]=o.useState(!1),[x,u]=o.useState(!1),[b,k]=o.useState(null),[L,C]=o.useState(!1),[N,j]=o.useState(!1),[A,_]=o.useState(null),[F,D]=o.useState(null),[B,X]=o.useState(!1),[I,O]=o.useState(!1),[Z,Re]=o.useState(!1),fe=o.useRef(void 0),{pushFrame:ne}=Qs(),je=o.useCallback(U=>{if(U.type==="session:joined"&&(p(!0),i.current({type:"device:boot",sessionId:e,payload:{deviceId:t,resetMode:s,acceptH264:_s(),secureContext:window.isSecureContext}})),U.type==="device:boot-error"&&D(U.message),U.type==="device:booting"&&(u(!1),C(!1),j(!1),_(null),D(null),k(null)),U.type==="device:ready"&&(u(!0),r&&(C(!0),i.current({type:"app:install",sessionId:e,buildId:r}))),U.type==="app:install-done"&&(C(!1),j(!0)),U.type==="app:install-error"&&(C(!1),_(U.message)),U.type==="app:launch-done"&&X(!1),U.type==="app:launch-error"&&X(!1),U.type==="session:chrome"&&k(U.payload),U.type==="keyboard:toggled"){const{visible:z}=U.payload;O(z),Re(!1)}U.type==="open-url:done"&&at.success("Deeplink opened"),U.type==="open-url:error"&&at.error(U.message),U.type==="error"&&U.message==="Agent resources exhausted"&&at.error("Could not start session — this Mac is currently overloaded.",{description:"Go back and select a different Mac."})},[e,t,r]),De=o.useCallback(U=>{var K;const z=Ws(U);if(z&&z.codec===bn){ne(U.slice(_t));return}z&&z.codec===mt||d.current.push(z);const le=z?U.slice(_t):U,Q=z?{codec:z.codec,keyframe:z.keyframe,capturedAt:z.capturedAt,relayedAt:z.relayedAt}:void 0;(K=fe.current)==null||K.call(fe,le,Q)},[ne]),{send:re,connected:E}=sn(je,De);o.useLayoutEffect(()=>{i.current=re}),o.useEffect(()=>{E&&re({type:"session:start",sessionId:e})},[E,re,e]);const V=b!==null&&"framePng"in b?b:null,Y=b!==null&&!("framePng"in b)?b:null,ke={sessionId:e,buildId:r,send:re,connected:E,joined:m,deviceReady:x,installing:L,installed:N,installError:A,bootError:F,launching:B,setLaunching:X,binaryFrameHandlerRef:fe,onRecordingUploaded:a,swKeyboardVisible:I,swKeyboardPending:Z,onKbdToggle:()=>{Re(!0),re({type:"input:keyboard:toggle",sessionId:e})}};if(!V&&!Y)return n.jsxs("div",{className:"flex items-start justify-center gap-16",children:[n.jsx("div",{className:"flex flex-col items-center gap-0.5 rounded-2xl border bg-background/90 px-1.5 py-2.5 shrink-0 mt-3 opacity-40",children:Array.from({length:5}).map((U,z)=>n.jsx("div",{className:"h-8 w-8 rounded-md bg-muted animate-pulse"},z))}),n.jsxs("div",{className:"flex items-start gap-8",children:[n.jsx("div",{style:{background:"#1c1c1e",borderRadius:"34px",padding:"12px",flexShrink:0},children:n.jsx("div",{className:"animate-pulse bg-zinc-700",style:{width:324,height:720,borderRadius:"22px"}})}),n.jsx(Pt,{joined:m,fps:0,connected:E,deviceReady:x,bootError:F,installing:L,installError:A,keyboardActive:!1})]})]});const se=void 0;return n.jsxs(n.Fragment,{children:[V&&n.jsx(Ys,{...ke,chrome:V,perfHookRef:se}),Y&&n.jsx(Gs,{...ke,androidButtons:Y.buttons,screenWidth:Y.screenWidth,screenHeight:Y.screenHeight,cornerRadius:Y.cornerRadius,perfHookRef:se}),!1]})}const vn=o.forwardRef(({className:e,...t},r)=>n.jsx("textarea",{className:q("flex min-h-[80px] w-full rounded-md border border-input bg-background px-3 py-2 text-base ring-offset-background placeholder:text-muted-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50 md:text-sm",e),ref:r,...t}));vn.displayName="Textarea";function to(e,t){return o.useReducer((r,s)=>t[r][s]??r,e)}var At="ScrollArea",[wn]=nn(At),[no,xe]=wn(At),Sn=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,type:s="hover",dir:a,scrollHideDelay:i=600,...c}=e,[h,d]=o.useState(null),[m,p]=o.useState(null),[x,u]=o.useState(null),[b,k]=o.useState(null),[L,C]=o.useState(null),[N,j]=o.useState(0),[A,_]=o.useState(0),[F,D]=o.useState(!1),[B,X]=o.useState(!1),I=Fe(t,d),O=Gn(a);return n.jsx(no,{scope:r,type:s,dir:O,scrollHideDelay:i,scrollArea:h,viewport:m,onViewportChange:p,content:x,onContentChange:u,scrollbarX:b,onScrollbarXChange:k,scrollbarXEnabled:F,onScrollbarXEnabledChange:D,scrollbarY:L,onScrollbarYChange:C,scrollbarYEnabled:B,onScrollbarYEnabledChange:X,onCornerWidthChange:j,onCornerHeightChange:_,children:n.jsx(Ie.div,{dir:O,...c,ref:I,style:{position:"relative","--radix-scroll-area-corner-width":N+"px","--radix-scroll-area-corner-height":A+"px",...e.style}})})});Sn.displayName=At;var Rn="ScrollAreaViewport",jn=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,children:s,nonce:a,...i}=e,c=xe(Rn,r),h=o.useRef(null),d=Fe(t,h,c.onViewportChange);return n.jsxs(n.Fragment,{children:[n.jsx(ro,{nonce:a}),n.jsx(Ie.div,{"data-radix-scroll-area-viewport":"",...i,ref:d,style:{overflowX:c.scrollbarXEnabled?"scroll":"hidden",overflowY:c.scrollbarYEnabled?"scroll":"hidden",...e.style},children:n.jsx("div",{ref:c.onContentChange,style:{minWidth:"100%",display:"table"},children:s})})]})});jn.displayName=Rn;var ro=o.memo(({nonce:e})=>n.jsx("style",{dangerouslySetInnerHTML:{__html:"[data-radix-scroll-area-viewport]{scrollbar-width:none;-ms-overflow-style:none;-webkit-overflow-scrolling:touch;}[data-radix-scroll-area-viewport]::-webkit-scrollbar{display:none}"},nonce:e}),(e,t)=>e.nonce===t.nonce),Ne="ScrollAreaScrollbar",Dt=o.forwardRef((e,t)=>{const{forceMount:r,...s}=e,a=xe(Ne,e.__scopeScrollArea),{onScrollbarXEnabledChange:i,onScrollbarYEnabledChange:c}=a,h=e.orientation==="horizontal";return o.useEffect(()=>(h?i(!0):c(!0),()=>{h?i(!1):c(!1)}),[h,i,c]),a.type==="hover"?n.jsx(so,{...s,ref:t,forceMount:r}):a.type==="scroll"?n.jsx(oo,{...s,ref:t,forceMount:r}):a.type==="auto"?n.jsx(kn,{...s,ref:t,forceMount:r}):a.type==="always"?n.jsx(Lt,{...s,ref:t,"data-state":"visible"}):null});Dt.displayName=Ne;var so=o.forwardRef((e,t)=>{const{forceMount:r,...s}=e,a=xe(Ne,e.__scopeScrollArea),[i,c]=o.useState(!1);return o.useEffect(()=>{const h=a.scrollArea;let d=0;if(h){const m=()=>{window.clearTimeout(d),c(!0)},p=()=>{d=window.setTimeout(()=>c(!1),a.scrollHideDelay)};return h.addEventListener("pointerenter",m),h.addEventListener("pointerleave",p),()=>{window.clearTimeout(d),h.removeEventListener("pointerenter",m),h.removeEventListener("pointerleave",p)}}},[a.scrollArea,a.scrollHideDelay]),n.jsx(bt,{present:r||i,children:n.jsx(kn,{"data-state":i?"visible":"hidden",...s,ref:t})})}),oo=o.forwardRef((e,t)=>{const{forceMount:r,...s}=e,a=xe(Ne,e.__scopeScrollArea),i=e.orientation==="horizontal",c=vt(()=>d("SCROLL_END"),100),[h,d]=to("hidden",{hidden:{SCROLL:"scrolling"},scrolling:{SCROLL_END:"idle",POINTER_ENTER:"interacting"},interacting:{SCROLL:"interacting",POINTER_LEAVE:"idle"},idle:{HIDE:"hidden",SCROLL:"scrolling",POINTER_ENTER:"interacting"}});return o.useEffect(()=>{if(h==="idle"){const m=window.setTimeout(()=>d("HIDE"),a.scrollHideDelay);return()=>window.clearTimeout(m)}},[h,a.scrollHideDelay,d]),o.useEffect(()=>{const m=a.viewport,p=i?"scrollLeft":"scrollTop";if(m){let x=m[p];const u=()=>{const b=m[p];x!==b&&(d("SCROLL"),c()),x=b};return m.addEventListener("scroll",u),()=>m.removeEventListener("scroll",u)}},[a.viewport,i,d,c]),n.jsx(bt,{present:r||h!=="hidden",children:n.jsx(Lt,{"data-state":h==="hidden"?"hidden":"visible",...s,ref:t,onPointerEnter:Ue(e.onPointerEnter,()=>d("POINTER_ENTER")),onPointerLeave:Ue(e.onPointerLeave,()=>d("POINTER_LEAVE"))})})}),kn=o.forwardRef((e,t)=>{const r=xe(Ne,e.__scopeScrollArea),{forceMount:s,...a}=e,[i,c]=o.useState(!1),h=e.orientation==="horizontal",d=vt(()=>{if(r.viewport){const m=r.viewport.offsetWidth<r.viewport.scrollWidth,p=r.viewport.offsetHeight<r.viewport.scrollHeight;c(h?m:p)}},10);return et(r.viewport,d),et(r.content,d),n.jsx(bt,{present:s||i,children:n.jsx(Lt,{"data-state":i?"visible":"hidden",...a,ref:t})})}),Lt=o.forwardRef((e,t)=>{const{orientation:r="vertical",...s}=e,a=xe(Ne,e.__scopeScrollArea),i=o.useRef(null),c=o.useRef(0),[h,d]=o.useState({content:0,viewport:0,scrollbar:{size:0,paddingStart:0,paddingEnd:0}}),m=Tn(h.viewport,h.content),p={...s,sizes:h,onSizesChange:d,hasThumb:m>0&&m<1,onThumbChange:u=>i.current=u,onThumbPointerUp:()=>c.current=0,onThumbPointerDown:u=>c.current=u};function x(u,b){return fo(u,c.current,h,b)}return r==="horizontal"?n.jsx(ao,{...p,ref:t,onThumbPositionChange:()=>{if(a.viewport&&i.current){const u=a.viewport.scrollLeft,b=qt(u,h,a.dir);i.current.style.transform=`translate3d(${b}px, 0, 0)`}},onWheelScroll:u=>{a.viewport&&(a.viewport.scrollLeft=u)},onDragScroll:u=>{a.viewport&&(a.viewport.scrollLeft=x(u,a.dir))}}):r==="vertical"?n.jsx(io,{...p,ref:t,onThumbPositionChange:()=>{if(a.viewport&&i.current){const u=a.viewport.scrollTop,b=qt(u,h);i.current.style.transform=`translate3d(0, ${b}px, 0)`}},onWheelScroll:u=>{a.viewport&&(a.viewport.scrollTop=u)},onDragScroll:u=>{a.viewport&&(a.viewport.scrollTop=x(u))}}):null}),ao=o.forwardRef((e,t)=>{const{sizes:r,onSizesChange:s,...a}=e,i=xe(Ne,e.__scopeScrollArea),[c,h]=o.useState(),d=o.useRef(null),m=Fe(t,d,i.onScrollbarXChange);return o.useEffect(()=>{d.current&&h(getComputedStyle(d.current))},[d]),n.jsx(En,{"data-orientation":"horizontal",...a,ref:m,sizes:r,style:{bottom:0,left:i.dir==="rtl"?"var(--radix-scroll-area-corner-width)":0,right:i.dir==="ltr"?"var(--radix-scroll-area-corner-width)":0,"--radix-scroll-area-thumb-width":yt(r)+"px",...e.style},onThumbPointerDown:p=>e.onThumbPointerDown(p.x),onDragScroll:p=>e.onDragScroll(p.x),onWheelScroll:(p,x)=>{if(i.viewport){const u=i.viewport.scrollLeft+p.deltaX;e.onWheelScroll(u),An(u,x)&&p.preventDefault()}},onResize:()=>{d.current&&i.viewport&&c&&s({content:i.viewport.scrollWidth,viewport:i.viewport.offsetWidth,scrollbar:{size:d.current.clientWidth,paddingStart:xt(c.paddingLeft),paddingEnd:xt(c.paddingRight)}})}})}),io=o.forwardRef((e,t)=>{const{sizes:r,onSizesChange:s,...a}=e,i=xe(Ne,e.__scopeScrollArea),[c,h]=o.useState(),d=o.useRef(null),m=Fe(t,d,i.onScrollbarYChange);return o.useEffect(()=>{d.current&&h(getComputedStyle(d.current))},[d]),n.jsx(En,{"data-orientation":"vertical",...a,ref:m,sizes:r,style:{top:0,right:i.dir==="ltr"?0:void 0,left:i.dir==="rtl"?0:void 0,bottom:"var(--radix-scroll-area-corner-height)","--radix-scroll-area-thumb-height":yt(r)+"px",...e.style},onThumbPointerDown:p=>e.onThumbPointerDown(p.y),onDragScroll:p=>e.onDragScroll(p.y),onWheelScroll:(p,x)=>{if(i.viewport){const u=i.viewport.scrollTop+p.deltaY;e.onWheelScroll(u),An(u,x)&&p.preventDefault()}},onResize:()=>{d.current&&i.viewport&&c&&s({content:i.viewport.scrollHeight,viewport:i.viewport.offsetHeight,scrollbar:{size:d.current.clientHeight,paddingStart:xt(c.paddingTop),paddingEnd:xt(c.paddingBottom)}})}})}),[co,Cn]=wn(Ne),En=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,sizes:s,hasThumb:a,onThumbChange:i,onThumbPointerUp:c,onThumbPointerDown:h,onThumbPositionChange:d,onDragScroll:m,onWheelScroll:p,onResize:x,...u}=e,b=xe(Ne,r),[k,L]=o.useState(null),C=Fe(t,L),N=o.useRef(null),j=o.useRef(""),A=b.viewport,_=s.content-s.viewport,F=qe(p),D=qe(d),B=vt(x,10);function X(I){if(N.current){const O=I.clientX-N.current.left,Z=I.clientY-N.current.top;m({x:O,y:Z})}}return o.useEffect(()=>{const I=O=>{const Z=O.target;(k==null?void 0:k.contains(Z))&&F(O,_)};return document.addEventListener("wheel",I,{passive:!1}),()=>document.removeEventListener("wheel",I,{passive:!1})},[A,k,_,F]),o.useEffect(D,[s,D]),et(k,B),et(b.content,B),n.jsx(co,{scope:r,scrollbar:k,hasThumb:a,onThumbChange:qe(i),onThumbPointerUp:qe(c),onThumbPositionChange:D,onThumbPointerDown:qe(h),children:n.jsx(Ie.div,{...u,ref:C,style:{position:"absolute",...u.style},onPointerDown:Ue(e.onPointerDown,I=>{I.button===0&&(I.target.setPointerCapture(I.pointerId),N.current=k.getBoundingClientRect(),j.current=document.body.style.webkitUserSelect,document.body.style.webkitUserSelect="none",b.viewport&&(b.viewport.style.scrollBehavior="auto"),X(I))}),onPointerMove:Ue(e.onPointerMove,X),onPointerUp:Ue(e.onPointerUp,I=>{const O=I.target;O.hasPointerCapture(I.pointerId)&&O.releasePointerCapture(I.pointerId),document.body.style.webkitUserSelect=j.current,b.viewport&&(b.viewport.style.scrollBehavior=""),N.current=null})})})}),gt="ScrollAreaThumb",Nn=o.forwardRef((e,t)=>{const{forceMount:r,...s}=e,a=Cn(gt,e.__scopeScrollArea);return n.jsx(bt,{present:r||a.hasThumb,children:n.jsx(lo,{ref:t,...s})})}),lo=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,style:s,...a}=e,i=xe(gt,r),c=Cn(gt,r),{onThumbPositionChange:h}=c,d=Fe(t,c.onThumbChange),m=o.useRef(void 0),p=vt(()=>{m.current&&(m.current(),m.current=void 0)},100);return o.useEffect(()=>{const x=i.viewport;if(x){const u=()=>{if(p(),!m.current){const b=ho(x,h);m.current=b,h()}};return h(),x.addEventListener("scroll",u),()=>x.removeEventListener("scroll",u)}},[i.viewport,p,h]),n.jsx(Ie.div,{"data-state":c.hasThumb?"visible":"hidden",...a,ref:d,style:{width:"var(--radix-scroll-area-thumb-width)",height:"var(--radix-scroll-area-thumb-height)",...s},onPointerDownCapture:Ue(e.onPointerDownCapture,x=>{const b=x.target.getBoundingClientRect(),k=x.clientX-b.left,L=x.clientY-b.top;c.onThumbPointerDown({x:k,y:L})}),onPointerUp:Ue(e.onPointerUp,c.onThumbPointerUp)})});Nn.displayName=gt;var Mt="ScrollAreaCorner",_n=o.forwardRef((e,t)=>{const r=xe(Mt,e.__scopeScrollArea),s=!!(r.scrollbarX&&r.scrollbarY);return r.type!=="scroll"&&s?n.jsx(uo,{...e,ref:t}):null});_n.displayName=Mt;var uo=o.forwardRef((e,t)=>{const{__scopeScrollArea:r,...s}=e,a=xe(Mt,r),[i,c]=o.useState(0),[h,d]=o.useState(0),m=!!(i&&h),{onCornerWidthChange:p,onCornerHeightChange:x}=a;return et(a.scrollbarX,()=>{var b;const u=((b=a.scrollbarX)==null?void 0:b.offsetHeight)||0;a.onCornerHeightChange(u),d(u)}),et(a.scrollbarY,()=>{var b;const u=((b=a.scrollbarY)==null?void 0:b.offsetWidth)||0;a.onCornerWidthChange(u),c(u)}),o.useEffect(()=>()=>{p(0),x(0)},[p,x]),m?n.jsx(Ie.div,{...s,ref:t,style:{width:i,height:h,position:"absolute",right:a.dir==="ltr"?0:void 0,left:a.dir==="rtl"?0:void 0,bottom:0,...e.style}}):null});function xt(e){return e?parseInt(e,10):0}function Tn(e,t){const r=e/t;return isNaN(r)?0:r}function yt(e){const t=Tn(e.viewport,e.content),r=e.scrollbar.paddingStart+e.scrollbar.paddingEnd,s=(e.scrollbar.size-r)*t;return Math.max(s,18)}function fo(e,t,r,s="ltr"){const a=yt(r),i=a/2,c=t||i,h=a-c,d=r.scrollbar.paddingStart+c,m=r.scrollbar.size-r.scrollbar.paddingEnd-h,p=r.content-r.viewport,x=s==="ltr"?[0,p]:[p*-1,0];return Pn([d,m],x)(e)}function qt(e,t,r="ltr"){const s=yt(t),a=t.scrollbar.paddingStart+t.scrollbar.paddingEnd,i=t.scrollbar.size-a,c=t.content-t.viewport,h=i-s,d=r==="ltr"?[0,c]:[c*-1,0],m=pr(e,d);return Pn([0,c],[0,h])(m)}function Pn(e,t){return r=>{if(e[0]===e[1]||t[0]===t[1])return t[0];const s=(t[1]-t[0])/(e[1]-e[0]);return t[0]+s*(r-e[0])}}function An(e,t){return e>0&&e<t}var ho=(e,t=()=>{})=>{let r={left:e.scrollLeft,top:e.scrollTop},s=0;return(function a(){const i={left:e.scrollLeft,top:e.scrollTop},c=r.left!==i.left,h=r.top!==i.top;(c||h)&&t(),r=i,s=window.requestAnimationFrame(a)})(),()=>window.cancelAnimationFrame(s)};function vt(e,t){const r=qe(e),s=o.useRef(0);return o.useEffect(()=>()=>window.clearTimeout(s.current),[]),o.useCallback(()=>{window.clearTimeout(s.current),s.current=window.setTimeout(r,t)},[r,t])}function et(e,t){const r=qe(t);qn(()=>{let s=0;if(e){const a=new ResizeObserver(()=>{cancelAnimationFrame(s),s=window.requestAnimationFrame(r)});return a.observe(e),()=>{window.cancelAnimationFrame(s),a.unobserve(e)}}},[e,r])}var Dn=Sn,po=jn,mo=_n;const Ln=o.forwardRef(({className:e,children:t,...r},s)=>n.jsxs(Dn,{ref:s,className:q("relative overflow-hidden",e),...r,children:[n.jsx(po,{className:"h-full w-full rounded-[inherit]",children:t}),n.jsx(Mn,{}),n.jsx(mo,{})]}));Ln.displayName=Dn.displayName;const Mn=o.forwardRef(({className:e,orientation:t="vertical",...r},s)=>n.jsx(Dt,{ref:s,orientation:t,className:q("flex touch-none select-none transition-colors",t==="vertical"&&"h-full w-2.5 border-l border-l-transparent p-[1px]",t==="horizontal"&&"h-2.5 flex-col border-t border-t-transparent p-[1px]",e),...r,children:n.jsx(Nn,{className:"relative flex-1 rounded-full bg-border"})}));Mn.displayName=Dt.displayName;function Hn(e){return/[Zz]|[+-]\d{2}/.test(e)?new Date(e):new Date(e.replace(" ","T")+"Z")}function go(e){const t=new Map;for(const a of e){const i=Hn(a.created_at).toDateString();t.has(i)||t.set(i,[]),t.get(i).push(a)}const r=new Date().toDateString(),s=new Date(Date.now()-864e5).toDateString();return Array.from(t.entries()).map(([a,i])=>{let c;if(a===r)c="Today";else if(a===s)c="Yesterday";else{const h=new Date(a);c=h.toLocaleDateString(void 0,{month:"short",day:"numeric",...h.getFullYear()!==new Date().getFullYear()?{year:"numeric"}:{}})}return{label:c,items:i}})}function xo(e){return Hn(e).toLocaleTimeString(void 0,{hour:"numeric",minute:"2-digit"})}const bo=5*1024*1024,yo=["image/png","image/jpeg","image/webp"];function vo({buildId:e}){const[t,r]=o.useState([]),[s,a]=o.useState(""),[i,c]=o.useState(null),[h,d]=o.useState(!1),[m,p]=o.useState(""),x=o.useRef(null),u=o.useRef({});function b(){fetch(`/api/v1/comments?build_id=${e}`,{credentials:"include"}).then(j=>j.ok?j.json():[]).then(r)}o.useEffect(()=>{b()},[e]),o.useEffect(()=>{const j=window.location.hash;if(!j.startsWith("#comment-"))return;const A=Number(j.replace("#comment-","")),_=u.current[A];if(!_)return;_.scrollIntoView({behavior:"smooth"});const F=document.documentElement.classList.contains("dark");_.style.backgroundColor=F?"rgb(0 112 243 / 0.18)":"#d3e5ff",setTimeout(()=>{_.style.backgroundColor=""},2e3)},[t]);function k(j){const A=`${location.origin}${location.pathname}${location.search}#comment-${j}`;navigator.clipboard.writeText(A).then(()=>at.success("Link copied")).catch(()=>at.error("Could not copy link"))}function L(j){if(p(""),!yo.includes(j.type)){p("Only png, jpg, webp allowed");return}if(j.size>bo){p("Max 5MB");return}c(j)}async function C(j){if(j.preventDefault(),!s.trim()&&!i)return;d(!0);const A=new FormData;A.append("build_id",String(e)),A.append("body",s),i&&A.append("attachment",i),(await fetch("/api/v1/comments",{method:"POST",credentials:"include",body:A})).ok&&(a(""),c(null),b()),d(!1)}const N=go(t);return n.jsxs("div",{className:"flex h-full flex-col gap-3 px-1",children:[n.jsx(Ln,{className:"flex-1 rounded-md border",children:n.jsx("div",{className:"p-3",children:t.length===0?n.jsx("p",{className:"text-sm text-muted-foreground text-center py-8",children:"No comments yet."}):n.jsx("div",{className:"flex flex-col",children:N.map(({label:j,items:A})=>n.jsxs("div",{children:[n.jsxs("div",{className:"flex items-center gap-2 py-3",children:[n.jsx("div",{className:"h-px flex-1 bg-border"}),n.jsx("span",{className:"text-[11px] font-medium text-muted-foreground px-1 select-none",children:j}),n.jsx("div",{className:"h-px flex-1 bg-border"})]}),n.jsx("div",{className:"flex flex-col gap-4",children:A.map(_=>n.jsxs("div",{id:`comment-${_.id}`,ref:F=>{u.current[_.id]=F},className:"group flex gap-2.5 rounded-md px-2 py-1.5 transition-all",children:[n.jsx("div",{className:"mt-0.5 shrink-0",children:n.jsx(Jn,{name:_.author,avatarUrl:_.authorAvatarUrl,size:28})}),n.jsxs("div",{className:"flex-1 min-w-0",children:[n.jsxs("div",{className:"flex items-center gap-1.5",children:[n.jsx("span",{className:"text-sm font-semibold leading-none",children:_.author}),n.jsx("span",{className:"text-[11px] text-muted-foreground leading-none",children:xo(_.created_at)}),n.jsx(ee,{variant:"ghost",size:"icon",className:"h-4 w-4 ml-0.5 opacity-0 group-hover:opacity-50 hover:!opacity-100 transition-opacity",onClick:()=>k(_.id),children:n.jsx(un,{className:"h-3 w-3"})})]}),n.jsx("p",{className:"text-sm leading-relaxed whitespace-pre-wrap mt-1",children:_.body}),_.attachments.map(F=>n.jsx("a",{href:F.file_path,target:"_blank",rel:"noreferrer",className:"mt-1.5 block",children:n.jsx("img",{src:F.file_path,alt:"attachment",className:"max-h-48 rounded border object-contain"})},F.id))]})]},_.id))})]},j))})})}),n.jsx("div",{className:"pb-1",children:n.jsx("form",{onSubmit:C,children:n.jsxs("div",{className:"rounded-xl border border-input bg-background ring-offset-background transition-shadow focus-within:outline-none focus-within:ring-2 focus-within:ring-ring focus-within:ring-offset-2",children:[n.jsx(vn,{placeholder:"Leave a comment…",value:s,onChange:j=>a(j.target.value),className:"min-h-16 resize-none border-0 bg-transparent shadow-none focus-visible:ring-0 focus-visible:ring-offset-0 text-sm"}),(i||m)&&n.jsxs("div",{className:"px-3 -mt-1 pb-1",children:[i&&n.jsx("p",{className:"text-xs text-muted-foreground",children:i.name}),m&&n.jsx("p",{className:"text-xs text-destructive",children:m})]}),n.jsxs("div",{className:"flex items-center gap-2 px-2 py-2",children:[n.jsx(ee,{type:"button",variant:"ghost",size:"icon",className:"h-7 w-7 text-muted-foreground",onClick:()=>{var j;return(j=x.current)==null?void 0:j.click()},children:n.jsx(Dr,{className:"h-4 w-4"})}),n.jsx("input",{ref:x,type:"file",accept:"image/png,image/jpeg,image/webp",className:"hidden",onChange:j=>{var _;const A=(_=j.target.files)==null?void 0:_[0];A&&L(A)}}),n.jsx("div",{className:"flex-1"}),n.jsx(ee,{type:"submit",size:"icon",className:"h-7 w-7 rounded-full",disabled:h||!s.trim()&&!i,children:n.jsx(jr,{className:"h-3.5 w-3.5"})})]})]})})})]})}function wo(e){return e<1024*1024?`${(e/1024).toFixed(0)} KB`:`${(e/1024/1024).toFixed(1)} MB`}function So(e){return new Date(e).toLocaleString(void 0,{month:"short",day:"numeric",hour:"2-digit",minute:"2-digit"})}function Ro(e){const t=new Date(e).getTime()-Date.now();if(t<=0)return{label:"Expired",urgent:!0};const r=Math.floor(t/36e5);return r<1?{label:"< 1 hour left",urgent:!0}:r<24?{label:`Expires in ${r}h`,urgent:r<6}:{label:`Expires in ${Math.floor(r/24)}d`,urgent:!1}}function jo({buildId:e,refreshKey:t}){const[r,s]=o.useState([]),[a,i]=o.useState(!0),[c,h]=o.useState(!1);return o.useEffect(()=>{i(!0),h(!1);const d=setTimeout(()=>h(!0),250);return fetch(`/api/v1/recordings?buildId=${e}`,{credentials:"include"}).then(m=>m.ok?m.json():[]).then(m=>s(m)).catch(()=>s([])).finally(()=>{clearTimeout(d),i(!1)}),()=>clearTimeout(d)},[e,t]),a?c?n.jsx("p",{className:"text-xs text-muted-foreground",children:"Loading recordings…"}):null:r.length===0?n.jsx("p",{className:"py-8 text-center text-sm text-muted-foreground",children:"No recordings yet."}):n.jsx("div",{className:"flex flex-col gap-2",children:r.map(d=>{const m=Ro(d.expiresAt);return n.jsxs("div",{className:"flex items-center justify-between rounded-md border border-border px-3 py-2 text-sm",children:[n.jsxs("div",{className:"flex flex-col gap-0.5 min-w-0",children:[n.jsx("span",{className:"text-xs font-medium truncate",children:So(d.createdAt)}),n.jsxs("span",{className:`text-xs ${m.urgent?"text-destructive":"text-muted-foreground"}`,children:[m.label," · ",wo(d.fileSize)]})]}),n.jsx(ee,{variant:"ghost",size:"icon",className:"h-7 w-7 shrink-0 ml-2",title:"Download",onClick:()=>{const p=document.createElement("a");p.href=d.url,p.download="",p.click()},children:n.jsx(Nr,{className:"h-3.5 w-3.5"})})]},d.id)})})}function ko({buildId:e,recordingsRefreshKey:t=0}){return n.jsxs(lr,{defaultValue:"comments",className:"flex h-full flex-col",children:[n.jsx("div",{className:"shrink-0 px-1",children:n.jsxs(ur,{className:"w-full",children:[n.jsxs(Bt,{value:"comments",className:"flex-1 gap-1.5",children:[n.jsx(Br,{className:"h-3.5 w-3.5"}),"Comments"]}),n.jsxs(Bt,{value:"recordings",className:"flex-1 gap-1.5",children:[n.jsx(Tr,{className:"h-3.5 w-3.5"}),"Recordings"]})]})}),n.jsx(zt,{value:"comments",className:"mt-3 min-h-0 flex-1 overflow-hidden",children:n.jsx(vo,{buildId:e})}),n.jsx(zt,{value:"recordings",className:"mt-3 min-h-0 flex-1 overflow-y-auto",children:n.jsx(jo,{buildId:e,refreshKey:t})})]})}const Un=o.forwardRef(({...e},t)=>n.jsx("nav",{ref:t,"aria-label":"breadcrumb",...e}));Un.displayName="Breadcrumb";const Fn=o.forwardRef(({className:e,...t},r)=>n.jsx("ol",{ref:r,className:q("flex flex-wrap items-center gap-1.5 break-words text-sm text-muted-foreground sm:gap-2.5",e),...t}));Fn.displayName="BreadcrumbList";const ot=o.forwardRef(({className:e,...t},r)=>n.jsx("li",{ref:r,className:q("inline-flex items-center gap-1.5",e),...t}));ot.displayName="BreadcrumbItem";const dt=o.forwardRef(({asChild:e,className:t,...r},s)=>{const a=e?Zn:"a";return n.jsx(a,{ref:s,className:q("transition-colors hover:text-foreground cursor-pointer",t),...r})});dt.displayName="BreadcrumbLink";const ft=o.forwardRef(({className:e,...t},r)=>n.jsx("span",{ref:r,role:"link","aria-disabled":"true","aria-current":"page",className:q("font-medium text-foreground",e),...t}));ft.displayName="BreadcrumbPage";const ht=({children:e,className:t,...r})=>n.jsx("li",{role:"presentation","aria-hidden":"true",className:q("[&>svg]:h-3.5 [&>svg]:w-3.5",t),...r,children:e??n.jsx(Qn,{})});ht.displayName="BreadcrumbSeparator";var wt="Switch",[Co]=nn(wt),[Eo,Ht]=Co(wt);function No(e){const{__scopeSwitch:t,checked:r,children:s,defaultChecked:a,disabled:i,form:c,name:h,onCheckedChange:d,required:m,value:p="on",internal_do_not_use_render:x}=e,[u,b]=er({prop:r,defaultProp:a??!1,onChange:d,caller:wt}),[k,L]=o.useState(null),[C,N]=o.useState(null),j=o.useRef(!1),A=k?!!c||!!k.closest("form"):!0,_={checked:u,setChecked:b,disabled:i,control:k,setControl:L,name:h,form:c,value:p,hasConsumerStoppedPropagationRef:j,required:m,defaultChecked:a,isFormControl:A,bubbleInput:C,setBubbleInput:N};return n.jsx(Eo,{scope:t,..._,children:_o(x)?x(_):s})}var In="SwitchTrigger",$n=o.forwardRef(({__scopeSwitch:e,onClick:t,...r},s)=>{const{control:a,form:i,value:c,disabled:h,checked:d,required:m,setControl:p,setChecked:x,hasConsumerStoppedPropagationRef:u,isFormControl:b,bubbleInput:k}=Ht(In,e),L=Fe(s,p),C=o.useRef(d);return o.useEffect(()=>{const N=i?a==null?void 0:a.ownerDocument.getElementById(i):a==null?void 0:a.form;if(N instanceof HTMLFormElement){const j=()=>x(C.current);return N.addEventListener("reset",j),()=>N.removeEventListener("reset",j)}},[a,i,x]),n.jsx(Ie.button,{type:"button",role:"switch","aria-checked":d,"aria-required":m,"data-state":Vn(d),"data-disabled":h?"":void 0,disabled:h,value:c,...r,ref:L,onClick:Ue(t,N=>{x(j=>!j),k&&b&&(u.current=N.isPropagationStopped(),u.current||N.stopPropagation())})})});$n.displayName=In;var Ut=o.forwardRef((e,t)=>{const{__scopeSwitch:r,name:s,checked:a,defaultChecked:i,required:c,disabled:h,value:d,onCheckedChange:m,form:p,...x}=e;return n.jsx(No,{__scopeSwitch:r,checked:a,defaultChecked:i,disabled:h,required:c,onCheckedChange:m,name:s,form:p,value:d,internal_do_not_use_render:({isFormControl:u})=>n.jsxs(n.Fragment,{children:[n.jsx($n,{...x,ref:t,__scopeSwitch:r}),u&&n.jsx(Wn,{__scopeSwitch:r})]})})});Ut.displayName=wt;var Bn="SwitchThumb",zn=o.forwardRef((e,t)=>{const{__scopeSwitch:r,...s}=e,a=Ht(Bn,r);return n.jsx(Ie.span,{"data-state":Vn(a.checked),"data-disabled":a.disabled?"":void 0,...s,ref:t})});zn.displayName=Bn;var On="SwitchBubbleInput",Wn=o.forwardRef(({__scopeSwitch:e,...t},r)=>{const{control:s,hasConsumerStoppedPropagationRef:a,checked:i,defaultChecked:c,required:h,disabled:d,name:m,value:p,form:x,bubbleInput:u,setBubbleInput:b}=Ht(On,e),k=Fe(r,b),L=mr(i),C=tr(s);o.useEffect(()=>{const j=u;if(!j)return;const A=window.HTMLInputElement.prototype,F=Object.getOwnPropertyDescriptor(A,"checked").set,D=!a.current;if(L!==i&&F){const B=new Event("click",{bubbles:D});F.call(j,i),j.dispatchEvent(B)}},[u,L,i,a]);const N=o.useRef(i);return n.jsx(Ie.input,{type:"checkbox","aria-hidden":!0,defaultChecked:c??N.current,required:h,disabled:d,name:m,value:p,form:x,...t,tabIndex:-1,ref:k,style:{...t.style,...C,position:"absolute",pointerEvents:"none",opacity:0,margin:0,transform:"translateX(-100%)"}})});Wn.displayName=On;function _o(e){return typeof e=="function"}function Vn(e){return e?"checked":"unchecked"}const Xn=o.forwardRef(({className:e,...t},r)=>n.jsx(Ut,{className:q("peer inline-flex h-6 w-11 shrink-0 cursor-pointer items-center rounded-full border-2 border-transparent transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 focus-visible:ring-offset-background disabled:cursor-not-allowed disabled:opacity-50 data-[state=checked]:bg-primary data-[state=unchecked]:bg-input",e),...t,ref:r,children:n.jsx(zn,{className:q("pointer-events-none block h-5 w-5 rounded-full bg-background shadow-lg ring-0 transition-transform data-[state=checked]:translate-x-5 data-[state=unchecked]:translate-x-0")})}));Xn.displayName=Ut.displayName;const Jt=70,Zt=80;function To(e,t){if(!e||t)return"unknown";const r=e.memUsedMB/e.memTotalMB*100;return e.cpuPercent>Zt||r>Zt?"overloaded":e.cpuPercent>=Jt||r>=Jt?"warning":"healthy"}function Uo(){const[e]=en(),t=nr(),r=e.get("id"),{build:s}=ns(r),[a,i]=o.useState(0),c=(s==null?void 0:s.platform)??"ios",{sessions:h,selectedAgent:d,setSelectedAgent:m,activeSessionId:p,deviceId:x,booting:u,status:b,connected:k,agentGroups:L,startDevice:C,resetDevice:N,handleBack:j,handleBackToMacs:A}=rs(c),_=L.find(E=>E.agentName===d),{osVersions:F,osVersion:D,setOsVersion:B,deviceSearch:X,setDeviceSearch:I,versionedDevices:O,resetMode:Z,setResetMode:Re}=ss(_,c),ne=h.flatMap(E=>E.devices).find(E=>E.id===x),je=ne?`${ne.name}${ne.osVersion?` · ${ne.osVersion}`:""}`:"",De=o.useCallback(()=>i(E=>E+1),[]),{setNode:re}=rr();return o.useEffect(()=>{if(s)return re(n.jsxs("div",{className:"flex items-center gap-3",children:[n.jsx(Un,{children:n.jsxs(Fn,{children:[n.jsx(ot,{children:n.jsx(dt,{asChild:!0,children:n.jsx("button",{onClick:()=>t(`/app-center?appId=${s.app_id}`),children:s.name})})}),n.jsx(ht,{}),n.jsx(ot,{children:d?n.jsx(dt,{asChild:!0,children:n.jsx("button",{onClick:A,children:$t(s)})}):n.jsx(ft,{children:$t(s)})}),d&&n.jsxs(n.Fragment,{children:[n.jsx(ht,{}),n.jsx(ot,{children:p?n.jsx(dt,{asChild:!0,children:n.jsx("button",{onClick:j,children:d})}):n.jsx(ft,{children:d})})]}),p&&n.jsxs(n.Fragment,{children:[n.jsx(ht,{}),n.jsx(ot,{children:n.jsx(ft,{children:je})})]})]})}),!d&&s.status_label&&n.jsx(vr,{tone:ir[s.status_label],children:s.status_label})]})),()=>re(null)},[s,d,p,je,t,j,A,re]),n.jsxs("div",{className:"flex h-full min-h-0 gap-6 p-6",children:[n.jsx("div",{className:"flex flex-col gap-3 flex-1 min-w-0 min-h-0",children:n.jsx("div",{className:"flex-1 min-h-0 overflow-auto -ml-1 pl-1 -mr-4 pr-4",children:p?n.jsx("div",{className:"min-h-full flex items-center justify-center py-6 px-8 min-w-max",children:n.jsx(eo,{sessionId:p,deviceId:x,buildId:s==null?void 0:s.id,resetMode:Z,onRecordingUploaded:De})}):d?n.jsxs("div",{className:"flex flex-col gap-5",children:[n.jsxs("div",{className:"flex items-center gap-3",children:[n.jsx("button",{onClick:A,className:"text-sm text-muted-foreground hover:text-foreground transition-colors",children:"← All Macs"}),n.jsx("h1",{className:"text-xl font-semibold tracking-tight",children:"Select device"})]}),n.jsxs("div",{className:"flex items-center gap-2",children:[n.jsx(cr,{placeholder:"Search device…",value:X,onChange:I}),F.length>0&&n.jsxs(gr,{value:D||"__all__",onValueChange:E=>{B(E==="__all__"?"":E),N()},children:[n.jsx(xr,{className:"h-8 w-36 shrink-0",children:n.jsx(br,{})}),n.jsxs(yr,{children:[n.jsx(Ot,{value:"__all__",children:"Any version"}),F.map(E=>n.jsx(Ot,{value:E,children:E},E))]})]}),n.jsx(Ct,{children:n.jsxs(ve,{children:[n.jsxs("div",{className:"ml-auto flex items-center gap-2 shrink-0",children:[n.jsx(we,{asChild:!0,children:n.jsxs(sr,{htmlFor:"reset-mode",className:"flex items-center gap-1 text-sm cursor-pointer whitespace-nowrap",children:[n.jsx(Mr,{className:"h-3.5 w-3.5 text-muted-foreground"}),"Full reset"]})}),n.jsx(Xn,{id:"reset-mode",checked:Z==="full-erase",onCheckedChange:E=>Re(E?"full-erase":"app-only")})]}),n.jsx(Se,{children:Z==="full-erase"?"Erase all data before booting":"Keep existing data"})]})})]}),O.length===0?n.jsx("p",{className:"text-sm text-muted-foreground",children:k?"No devices available for this OS.":"Connecting to relay…"}):n.jsx("div",{className:"grid grid-cols-1 lg:grid-cols-2 2xl:grid-cols-3 gap-2",children:O.map(E=>{const V=E.status==="booted",Y=E.busy,ce=Y?"In use":V?"Booted":"Available",ke=Y?"bg-amber-400":V?"bg-emerald-400":"bg-muted-foreground/40";return n.jsxs("button",{disabled:Y||u||!k,onClick:()=>C(E),className:q("flex flex-col gap-3 rounded-lg border p-3 text-left transition-colors min-h-[100px]","hover:bg-accent disabled:cursor-not-allowed disabled:opacity-50"),children:[n.jsx("span",{className:"text-sm font-medium leading-tight",children:E.name}),E.osVersion&&n.jsx("span",{className:"font-mono text-xs text-muted-foreground",children:E.osVersion}),n.jsxs("span",{className:"flex items-center gap-1.5 text-xs text-muted-foreground",children:[n.jsx("span",{className:q("inline-block h-1.5 w-1.5 rounded-full",ke)}),ce]})]},E.id)})}),b&&n.jsx("p",{className:"text-sm text-muted-foreground",children:b})]}):n.jsxs("div",{className:"flex flex-col gap-5",children:[n.jsx("h1",{className:"text-xl font-semibold tracking-tight",children:"Select Mac"}),L.length===0?n.jsx("p",{className:"text-sm text-muted-foreground",children:k?`No agents available for ${c}.`:"Connecting to relay…"}):n.jsx("div",{className:"grid grid-cols-1 lg:grid-cols-2 2xl:grid-cols-3 gap-2",children:L.map(E=>{const V=E.resources,Y=V?Date.now()-V.reportedAt>3e4:!1,ce=E.devices.filter(le=>le.platform===c).length,ke=(V==null?void 0:V.cpuPercent)??0,se=V?V.memUsedMB/V.memTotalMB*100:0,U=To(V,Y),z=U==="overloaded";return n.jsx(Ct,{children:n.jsxs(ve,{children:[n.jsx(we,{asChild:!0,children:n.jsx("span",{tabIndex:z?0:void 0,className:z?"cursor-not-allowed":void 0,children:n.jsxs("button",{disabled:z,"aria-disabled":z,onClick:()=>m(E.agentName??null),className:q("flex flex-col gap-3 rounded-lg border p-3 text-left transition-colors min-h-[100px] w-full",z?"pointer-events-none":"hover:bg-accent"),children:[n.jsxs("div",{className:"flex items-start justify-between gap-2",children:[n.jsxs("div",{className:"flex items-center gap-2 min-w-0",children:[n.jsx(Po,{health:U}),n.jsx("span",{className:"text-sm font-medium leading-tight truncate",children:E.agentName??"Unknown"})]}),Y&&n.jsx("span",{className:"shrink-0 text-[10px] font-medium text-amber-500",children:"Stale"})]}),n.jsxs("div",{className:"flex items-center gap-1.5 text-xs text-muted-foreground",children:[n.jsxs("span",{children:[ce," device",ce!==1?"s":""]}),V&&n.jsxs(n.Fragment,{children:[n.jsx("span",{children:"·"}),n.jsxs("span",{children:[V.slotsAvailable,"/",V.slotsTotal," slots"]})]})]}),V&&!Y&&n.jsxs("div",{className:"flex flex-col gap-1.5 w-full",children:[n.jsx(Qt,{label:"CPU",percent:ke,colorClass:"bg-blue-400"}),n.jsx(Qt,{label:"RAM",percent:se,colorClass:"bg-violet-400"})]})]})})}),z&&n.jsx(Se,{children:"This Mac is currently overloaded. Try again later."})]})},E.agentName)})})]})})}),r&&n.jsxs(n.Fragment,{children:[n.jsx(tn,{orientation:"vertical",className:"h-auto"}),n.jsx("div",{className:"w-80 shrink-0 h-full",children:n.jsx(ko,{buildId:Number(r),recordingsRefreshKey:a})})]})]})}function Po({health:e}){const t={unknown:"bg-muted-foreground/40",healthy:"bg-emerald-400",warning:"bg-amber-400",overloaded:"bg-red-500"}[e];return n.jsx("span",{"data-testid":"resource-health-dot",className:q("inline-block h-2 w-2 shrink-0 rounded-full",t)})}function Qt({label:e,percent:t,colorClass:r}){return n.jsxs("div",{className:"flex flex-col gap-0.5",children:[n.jsxs("div",{className:"flex justify-between text-[10px] text-muted-foreground",children:[n.jsx("span",{children:e}),n.jsxs("span",{children:[t.toFixed(0),"%"]})]}),n.jsx("div",{className:"h-1 w-full rounded-full bg-muted overflow-hidden",children:n.jsx("div",{className:q("h-full rounded-full transition-all",r),style:{width:`${Math.min(100,t)}%`}})})]})}export{Uo as QASession};
|
|
Binary file
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{al as b,am as S,a7 as m,ai as k,aa as C,a4 as s,C as h,d as p,e as x,c as f,b as P,L as u,I as w,B as E,a5 as F,a8 as j}from"./index-
|
|
1
|
+
import{al as b,am as S,a7 as m,ai as k,aa as C,a4 as s,C as h,d as p,e as x,c as f,b as P,L as u,I as w,B as E,a5 as F,a8 as j}from"./index-IvDXNTVd.js";const T=F({password:j().min(8),confirm:j()}).refine(r=>r.password===r.confirm,{message:"Passwords do not match",path:["confirm"]});function L(){const r=b(),[g]=S(),a=g.get("token")??"",[n,t]=m.useState("loading"),{register:o,handleSubmit:v,setError:d,formState:{errors:e,isSubmitting:c}}=k({resolver:C(T),mode:"onBlur"});m.useEffect(()=>{if(!a){t("invalid");return}fetch(`/api/v1/auth/reset-password/verify?token=${a}`).then(i=>i.ok?t("valid"):Promise.reject()).catch(()=>t("invalid"))},[a]);async function N(i){try{const l=await fetch("/api/v1/auth/reset-password",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({token:a,password:i.password})});if(!l.ok){const y=await l.json();d("root",{message:y.error??"Failed to reset password"});return}r("/login",{replace:!0})}catch{d("root",{message:"Network error. Please try again."})}}return n==="loading"?s.jsx("div",{className:"flex min-h-svh items-center justify-center"}):n==="invalid"?s.jsx("div",{className:"bg-mesh-gradient flex min-h-svh items-center justify-center overflow-hidden p-4",children:s.jsx(h,{level:4,className:"w-full max-w-sm text-center",children:s.jsxs(p,{children:[s.jsx(x,{children:"Link expired"}),s.jsx(f,{children:"This password reset link is invalid or has expired. Ask your admin to send a new one."})]})})}):s.jsx("div",{className:"bg-mesh-gradient flex min-h-svh items-center justify-center overflow-hidden p-4",children:s.jsxs(h,{level:4,className:"w-full max-w-sm",children:[s.jsxs(p,{className:"text-center",children:[s.jsx(x,{children:"Reset password"}),s.jsx(f,{children:"Enter your new password below."})]}),s.jsx(P,{children:s.jsxs("form",{onSubmit:v(N),className:"flex flex-col gap-4",children:[s.jsxs("div",{className:"grid gap-2",children:[s.jsx(u,{htmlFor:"password",children:"New password"}),s.jsx(w,{id:"password",type:"password",...o("password")}),e.password&&s.jsx("p",{className:"text-sm text-destructive",children:e.password.message})]}),s.jsxs("div",{className:"grid gap-2",children:[s.jsx(u,{htmlFor:"confirm",children:"Confirm password"}),s.jsx(w,{id:"confirm",type:"password",...o("confirm")}),e.confirm&&s.jsx("p",{className:"text-sm text-destructive",children:e.confirm.message})]}),e.root&&s.jsx("p",{className:"text-sm text-destructive",children:e.root.message}),s.jsx(E,{type:"submit",disabled:c,className:"w-full",children:c?"Saving…":"Set new password"})]})})]})})}export{L as ResetPassword};
|
|
Binary file
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{al as f,ap as g,ai as w,aa as j,a7 as v,a4 as e,C as N,d as b,e as y,b as C,L as i,I as o,B as S,a5 as k,a8 as l}from"./index-
|
|
1
|
+
import{al as f,ap as g,ai as w,aa as j,a7 as v,a4 as e,C as N,d as b,e as y,b as C,L as i,I as o,B as S,a5 as k,a8 as l}from"./index-IvDXNTVd.js";const E=k({email:l().email("Enter a valid email"),password:l().min(8,"Password must be at least 8 characters"),confirm:l()}).refine(a=>a.password===a.confirm,{message:"Passwords do not match",path:["confirm"]});function P(){const a=f(),{resolvedTheme:d}=g(),p=d==="dark"?"/logo-dark.svg":"/logo.svg",{register:r,handleSubmit:x,setError:c,formState:{errors:s,isSubmitting:n}}=w({resolver:j(E),mode:"onBlur"});v.useEffect(()=>{fetch("/api/v1/auth/status").then(t=>t.json()).then(({initialized:t})=>{t&&a("/login",{replace:!0})}).catch(()=>{})},[a]);async function h(t){try{const m=await fetch("/api/v1/auth/init",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({email:t.email,password:t.password})});if(!m.ok){const u=await m.json();c("root",{message:u.error??"Failed to create account"});return}a("/login",{replace:!0})}catch{c("root",{message:"Network error. Please try again."})}}return e.jsx("div",{className:"flex min-h-svh items-center justify-center overflow-hidden p-4",children:e.jsxs("div",{className:"flex flex-col items-center gap-6 w-full max-w-sm",children:[e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx("img",{src:p,alt:"tapflow",className:"w-6 h-6"}),e.jsx("span",{className:"text-base font-semibold tracking-tight",children:"tapflow"})]}),e.jsxs(N,{level:4,className:"w-full",children:[e.jsx(b,{className:"text-center",children:e.jsx(y,{className:"text-2xl tracking-display-md",children:"Set up tapflow"})}),e.jsx(C,{children:e.jsxs("form",{onSubmit:x(h),className:"flex flex-col gap-4",children:[e.jsxs("div",{className:"grid gap-2",children:[e.jsx(i,{htmlFor:"email",children:"Admin email"}),e.jsx(o,{id:"email",type:"email",placeholder:"admin@yourteam.com",autoComplete:"email",...r("email")}),s.email&&e.jsx("p",{className:"text-sm text-destructive",children:s.email.message})]}),e.jsxs("div",{className:"grid gap-2",children:[e.jsx(i,{htmlFor:"password",children:"Password"}),e.jsx(o,{id:"password",type:"password",autoComplete:"new-password",...r("password")}),s.password&&e.jsx("p",{className:"text-sm text-destructive",children:s.password.message})]}),e.jsxs("div",{className:"grid gap-2",children:[e.jsx(i,{htmlFor:"confirm",children:"Confirm password"}),e.jsx(o,{id:"confirm",type:"password",autoComplete:"new-password",...r("confirm")}),s.confirm&&e.jsx("p",{className:"text-sm text-destructive",children:s.confirm.message})]}),s.root&&e.jsx("p",{className:"text-sm text-destructive",children:s.root.message}),e.jsx(S,{type:"submit",size:"lg",disabled:n,className:"w-full mt-1",children:n?"Creating account…":"Create admin account"})]})})]})]})})}export{P as Setup};
|
|
Binary file
|