videobook 0.2.4 → 0.3.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/CHANGELOG.md +38 -0
- package/README.md +6 -2
- package/dist/archive-b2.js +1 -1
- package/dist/cli/args.js +42 -3
- package/dist/cli/config-command.js +17 -1
- package/dist/cli/doctor-command.js +15 -0
- package/dist/cli/har-command.js +86 -0
- package/dist/cli/main.js +13 -1
- package/dist/command-reference.js +5 -1
- package/dist/content-store.js +2 -1
- package/dist/diagnostics.js +1 -1
- package/dist/env-secrets.js +1 -0
- package/dist/generation-har.js +106 -0
- package/dist/har-capture.js +142 -0
- package/dist/har-export.js +238 -0
- package/dist/har-index.js +98 -0
- package/dist/har-retention.js +73 -0
- package/dist/har-settings.js +27 -0
- package/dist/jobs/_alibaba-upload.js +2 -4
- package/dist/jobs/_fal-upload.js +2 -4
- package/dist/jobs/_image-edit-adapter.js +1 -1
- package/dist/jobs/_kie-upload.js +2 -4
- package/dist/jobs/complete-provider-task.js +5 -2
- package/dist/jobs/generate-media.js +9 -1
- package/dist/jobs/image-subjects.js +1 -1
- package/dist/jobs/kie-paygate.js +10 -3
- package/dist/jobs/run-notebook.js +4 -1
- package/dist/jobs/xai-paygate.js +5 -2
- package/dist/media/adapters/kie.js +2 -1
- package/dist/media/catalog.js +20 -0
- package/dist/media/cost.js +1 -1
- package/dist/package-version.js +18 -0
- package/dist/posts/dropbox-auth.js +1 -1
- package/dist/posts/post-metrics.js +2 -1
- package/dist/provider-usage.js +1 -18
- package/dist/queue.js +12 -1
- package/dist/serve.js +2 -0
- package/dist/tools/api-status.js +1 -1
- package/dist/tools/generate-media.js +3 -0
- package/dist/tools/generation-payload.js +17 -2
- package/dist/tools/get-generation-har.js +43 -0
- package/dist/tools/index.js +4 -0
- package/dist/tools/list-cell-generations.js +19 -0
- package/dist/tools/reconcile-project-work.js +18 -12
- package/dist/tools/set-har-capture.js +30 -0
- package/dist/upload.js +2 -1
- package/dist/usage-providers.js +48 -10
- package/dist/workspace-action-groups.js +2 -2
- package/dist/x/account.js +1 -1
- package/dist/x/authenticated-handle.js +1 -1
- package/dist/x/oauth-flow.js +1 -1
- package/dist/x/post-to-x.js +2 -1
- package/dist/x/x-tokens.js +2 -1
- package/package.json +15 -14
- package/ui/assets/{alive-captions-Bp6dxosy.js → alive-captions-Cj8C1tCN.js} +1 -1
- package/ui/assets/{confirm-bodies-Ds1HtaGc.js → confirm-bodies-BxWXwDf0.js} +1 -1
- package/ui/assets/{fullscreen-BCeVHjvY.js → fullscreen-DyEncSdm.js} +1 -1
- package/ui/assets/{goal-ui-DbAGwgMN.js → goal-ui-BdFeoSWh.js} +2 -2
- package/ui/assets/{index-D1d-F1y9.js → index-QZ8lbemN.js} +9 -9
- package/ui/assets/inspector-BC6xWkJU.js +1 -0
- package/ui/assets/{jobs-ui-C1cbw-xG.js → jobs-ui-BudI4w0r.js} +1 -1
- package/ui/assets/{music-video-CWtxPlxq.js → music-video-CT4C55ok.js} +1 -1
- package/ui/assets/ui-mq0uIS5P.css +1 -0
- package/ui/assets/ui-z5r-p0K9.js +2 -0
- package/ui/assets/{vendor-BFupLz37.js → vendor-D8XcMav4.js} +2 -2
- package/ui/assets/{vendor-flow-CKiuzaeM.js → vendor-flow-nqTFQmTh.js} +1 -1
- package/ui/assets/vendor-mcp-D_C3EZPv.js +60 -0
- package/ui/assets/videobook-CsW453sb.js +21 -0
- package/ui/index.html +12 -12
- package/ui/assets/inspector-BJTC0luH.js +0 -1
- package/ui/assets/ui-CXDi5Omq.js +0 -2
- package/ui/assets/ui-Oirr9VOf.css +0 -1
- package/ui/assets/vendor-mcp-DQEeVZH0.js +0 -67
- package/ui/assets/videobook-J-j9bSjM.js +0 -20
|
@@ -1,21 +1,21 @@
|
|
|
1
|
-
const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["assets/confirm-bodies-
|
|
2
|
-
import{a as m,j as C,d as pf}from"./vendor-react-Dj7D1fD4.js";import{i as gf,S as kf,b as ji,c as bf}from"./vendor-flow-CKiuzaeM.js";import{g as Us}from"./vendor-mcp-DQEeVZH0.js";import{y as ot,z as nt,E as wf,q as $i,F as hf,H as vf,J as yf,K as If,L as Cf,T as Sf,O as xf,Q as Ef,U as Af,n as _f,W as Rf,o as Pf,l as Mf,m as Tf,X as jf,Y as $f,Z as qf,_ as Nf,$ as Lf,a0 as Ff,a1 as Df,a2 as qi,p as Of,a3 as Vf,a4 as Gf,a5 as Uf}from"./ui-CXDi5Omq.js";import{ev as Wf,ew as zf,ex as Ni,ey as Li,ez as Is,eA as Bf,cE as Zn,eB as Hf,eC as Kf,eD as Jf,eE as Xf,eF as Qf,eG as Yf,eH as Zf,bH as _,bT as ie,eI as em,eJ as Fi,eK as eo,eL as tm,cL as Di,eM as Oi,eN as om,dp as nm,ds as rm,eO as Cs,eP as sm,eQ as am,eR as im,eS as lm,eT as Vi,eU as cm,eV as dm,eW as um,a as fm,eX as mm,eY as pm,eZ as gm,e_ as km,e$ as bm,bJ as D,cr as Gi,f0 as wm,f1 as hm,f2 as vm,f3 as ym,f4 as Nt,f5 as Im,f6 as Cm,f7 as Sm,f8 as Ui,f9 as ft,fa as L,fb as M,fc as Ss,fd as Wi,fe as xm,ff as Em,fg as Am,fh as ge,fi as to,fj as zi,fk as _m,fl as Rm,fm as Pm,fn as Lt,fo as Mm,fp as Tm,bA as Ft,fq as jm,fr as Bi,fs as er,ft as $m,fu as qm,fv as Hi,fw as Nm,fx as Lm,fy as Fm,fz as Ki,fA as Dm,fB as Om,fC as Vm,fD as pn,fE as Gm,fF as Ji,fG as Um,dB as Wm,fH as tr,dC as zm,dD as Bm,fI as Xi,fJ as Hm,fK as xs,fL as Km,fM as Jm,fN as Xm,fO as Qm,de as Ym,bR as Zm,fP as St,a8 as gn,fQ as ep,dh as Qi,fR as tp,fS as Yi,fT as Zi,fU as Ke,fV as op,fW as np,O as rp,fX as sp,fY as ap,fZ as ip,f_ as el,f$ as Es,g0 as tl,g1 as As,g2 as or,g3 as lp,g4 as cp,g5 as dp,g6 as up,g7 as fp,g8 as ol,g9 as mp,ga as pp,dO as nr,bC as gp,bB as kp,dA as bp,gb as wp,gc as hp,gd as vp,ge as nl,gf as yp,gg as Ip,gh as Cp,gi as rl,gj as Sp,co as xp,cp as Ep,am as Ap,cm as sl,gk as al,c1 as _p,cs as Rp,gl as Pp,gm as Mp,gn as _s,go as Tp,gp as jp,b8 as il,gq as Rs,gr as Mo,bK as Ps,bF as oo,a9 as $p,gs as ll,gt as qp,gu as Ms,gv as Np,gw as no,gx as Lp,gy as Fp,gz as Dp,gA as Op,gB as Vp,gC as Gp,gD as Ql,gE as Ts,gF as cl,gG as Up,gH as Wp,gI as zp,gJ as Bp,c6 as js,gK as dl,gL as Hp,gM as Kp,gN as Jp,gO as Xp,gP as Qp,gQ as Yp,gR as Zp,gS as eg,gT as ul,bY as Dt,gU as tg,gV as og,gW as fl,aa as ml,b1 as ng,gX as rg,bs as sg,gY as ag,dg as ig,gZ as lg,g_ as cg,g$ as dg,h0 as pl,h1 as ug,h2 as fg,h3 as mg,h4 as rr,h5 as pg,h6 as $s,h7 as gg,aL as kg,h8 as bg,aJ as wg,h9 as hg,ha as vg,hb as qs,hc as yg,hd as Ig,he as gl,hf as Cg,hg as kl,d6 as Sg,hh as bl,hi as xg,hj as Ns,hk as Eg,hl as sr,hm as Ag,hn as _g,ho as Rg,hp as Pg,hq as Mg,hr as Tg,hs as jg,b0 as $g,aH as qg,ht as Ng,hu as Lg,hv as Fg,hw as Dg,dj as wl,hx as Og,hy as hl,hz as kn,hA as ar,hB as Vg,hC as Gg,hD as Ug,hE as Wg,hF as zg,hG as Bg,hH as Hg,hI as Kg,hJ as Jg,hK as Xg,hL as vl,hM as Qg,hN as yl,hO as Yg,hP as Zg,hQ as ir,hR as ek,hS as tk,hT as ok,hU as nk,hV as rk,hW as sk,hX as Il,hY as ak,hZ as ik,h_ as lk,h$ as Cl,i0 as ck,i1 as Sl,i2 as dk,i3 as xl,i4 as uk,i5 as El,i6 as lr,i7 as Al,i8 as cr,i9 as _l,d7 as fk,ia as mk,N as pk,D as gk,ib as kk,ic as Ls,id as bk,ie as wk,ig as hk,ih as vk,ii as yk,ij as Ik,ik as Ck,il as Sk,im as xk,io as Ek,ip as Rl,iq as Ak,ir as _k,is as Rk,it as Pk,iu as Mk,iv as Tk,iw as jk,ix as Pl,iy as Po,iz as $k,iA as qk,Y as Nk,iB as Lk,iC as Fk,iD as Dk,iE as bn,iF as Ok,iG as Vk,iH as Gk,iI as Uk,iJ as Wk,iK as zk}from"./videobook-J-j9bSjM.js";import{a as Bk,T as Hk,G as Kk,P as Jk,C as Xk,S as Qk,b as Yk,R as Ml,N as Zk}from"./confirm-bodies-Ds1HtaGc.js";import{i as eb,A as Yl,n as Se,b as W,m as Tl,v as jl,x as dr,y as xt,Y as tb,f as pr,s as ob}from"./vendor-BFupLz37.js";import{J as nb}from"./jobs-ui-C1cbw-xG.js";import{N as rb}from"./inspector-BJTC0luH.js";import{N as sb}from"./fullscreen-BCeVHjvY.js";import{G as ab,a as ib,b as lb,c as cb}from"./goal-ui-DbAGwgMN.js";import{ar as db,z as $l,H as ub,B as fb,at as mb,a8 as pb,b as gb,au as kb}from"./vendor-icons-CGqhCIXV.js";import"./vendor-remotion-CH1HXrlc.js";(function(){const k=document.createElement("link").relList;if(k&&k.supports&&k.supports("modulepreload"))return;for(const I of document.querySelectorAll('link[rel="modulepreload"]'))b(I);new MutationObserver(I=>{for(const x of I)if(x.type==="childList")for(const j of x.addedNodes)j.tagName==="LINK"&&j.rel==="modulepreload"&&b(j)}).observe(document,{childList:!0,subtree:!0});function g(I){const x={};return I.integrity&&(x.integrity=I.integrity),I.referrerPolicy&&(x.referrerPolicy=I.referrerPolicy),I.crossOrigin==="use-credentials"?x.credentials="include":I.crossOrigin==="anonymous"?x.credentials="omit":x.credentials="same-origin",x}function b(I){if(I.ep)return;I.ep=!0;const x=g(I);fetch(I.href,x)}})();const we=f=>f.startsWith("@")?f.slice(1):f;function gr(f){const k=f.trim();if(k.length<2)return k;const g=k[0],b=k[k.length-1];return(g==='"'||g==="'")&&g===b?k.slice(1,-1).trim():k}const bb=/^[a-z0-9][a-z0-9-]*$/i;function wb(f){const k=f.asset_id;if(typeof k!="string"||!k.trim())throw new Error("/keywords requires a video cell or asset");const g=we(k.trim()),b=f.inputs;if(b===void 0)return{asset_id:g};if(!Array.isArray(b)||!b.every(j=>typeof j=="string"))throw new Error("/keywords inputs must be words");const I=b.map(j=>j.trim()).filter(Boolean);if(I.length===0)return{asset_id:g};const x=hb(I);return x?{asset_id:g,...x}:{asset_id:g,keywords:I}}function hb(f){const k=f[0]?.toLowerCase()??"",g=f.slice(1);if(["off","false","no","0"].includes(k))return g.length===0?{enabled:!1}:null;if(!["on","true","yes","1"].includes(k)||g.length>2)return null;if(g.length===0)return{enabled:!0};const b=Number(g[0]);if(!Number.isInteger(b)||b<1||b>20)return null;if(g.length===1)return{enabled:!0,max_keywords:b};const I=Number(g[1]);return!Number.isFinite(I)||I<.8||I>5?null:{enabled:!0,max_keywords:b,linger_seconds:I}}function vb(f){const k=f.toLowerCase();return k==="16:9"||k==="landscape"?"16:9":k==="9:16"||k==="portrait"?"9:16":k==="1:1"||k==="square"?"1:1":null}function yb(f){const k=f.map(we),g=[];let b;for(const I of k){const x=vb(I);if(x){if(b)throw new Error("/outroqr accepts only one aspect ratio");b=x;continue}if(!bb.test(I))throw new Error(`Unrecognized /outroqr input: ${I}`);if(g.push(I),g.length>4)throw new Error("/outroqr accepts at most 4 QR images")}if(g.length===0)throw new Error("/outroqr requires at least one QR image cell or asset");return{qr_image_refs:g,...b?{aspect_ratio:b}:{}}}function Ib(f){const k=f.asset_id,g=f.timestamp,b=f.type,I=f.description;if(typeof k!="string"||!k.trim())throw new Error("/apply-sfx requires a video cell or asset");const x=we(k.trim());if(typeof g!="string"&&typeof g!="number")throw new Error("/apply-sfx requires a timestamp");const j=typeof g=="number"?g:st(g,"/apply-sfx");if(!Number.isFinite(j)||j<0)throw new Error("/apply-sfx timestamp must be 0 or later");if(typeof b!="string"||!b.trim())throw new Error("/apply-sfx requires an effect type");if(typeof I!="string"||!I.trim())throw new Error("/apply-sfx requires an effect description");return{asset_id:x,sfx:[{timestamp:j,type:b.trim(),description:I.trim()}]}}function st(f,k){const b=f.trim().replace(/s$/i,"").split(":");if(b.length===1){const x=Number(b[0]);if(Number.isFinite(x)&&x>=0)return x;throw new Error(`Invalid ${k} timestamp: ${f}`)}if(b.length!==2&&b.length!==3)throw new Error(`Invalid ${k} timestamp: ${f}`);if(!b.every(x=>/^\d+(?:\.\d+)?$/.test(x)))throw new Error(`Invalid ${k} timestamp: ${f}`);const I=b.map(Number);return b.length===2?I[0]*60+I[1]:I[0]*3600+I[1]*60+I[2]}function Cb(f){const k=f.asset_id,g=f.range,b=f.factor;if(typeof k!="string"||!k.trim())throw new Error("/timewarp requires a video cell or asset");const I=we(k.trim());if(typeof g!="string")throw new Error("/timewarp requires a <start>-<end> range");const x=/^(.+)-(.+)$/.exec(g.trim());if(!x)throw new Error("/timewarp requires a <start>-<end> range");const j=st(x[1],"/timewarp"),i=st(x[2],"/timewarp");if(j>=i)throw new Error("/timewarp start must be before end");if(typeof b!="string"&&typeof b!="number")throw new Error("/timewarp requires a stretch factor");const K=String(b).trim();if(!/^\d+(?:\.\d+)?x?$/i.test(K))throw new Error(`Invalid /timewarp stretch factor: ${K}`);const c=Number(K.replace(/x$/i,""));if(!Number.isFinite(c)||c<.25||c>4)throw new Error("/timewarp stretch factor must be between 0.25x and 4x");if(c===1)throw new Error("/timewarp stretch factor 1x is a no-op");return{asset_id:I,start_seconds:j,end_seconds:i,stretch_factor:c}}function Sb(f){const k=f.trim(),g=k[0],b=k[k.length-1],I=g==='"'||g==="'";if(I||(b==='"'||b==="'")){if(!I||g!==b||k.length<2)throw new Error(`/sync-audio has mismatched quotes: ${f}`);return k.slice(1,-1).trim()}return k}function xb(f){const g=f.trim().replace(/s$/i,"").split(":");return g.length<1||g.length>3?!1:g.every(b=>/^\d+(?:\.\d+)?$/.test(b))}function Eb(f){const k=f.trim(),g=k.startsWith('"')||k.startsWith("'"),b=Sb(f);if(!b)throw new Error("/sync-audio anchor target cannot be empty");return!g&&xb(b)?{audio_seconds:st(b,"/sync-audio")}:{audio_cue:b}}function Ab(f){const k=f.asset_id,g=f.mappings;if(typeof k!="string"||!k.trim())throw new Error("/sync-audio requires a video cell or asset");const b=we(k.trim());if(typeof g!="string"||!g.trim())throw new Error("/sync-audio requires at least one video-time=audio-target mapping");const I=g.split(";"),x=[];for(const j of I){const i=j.indexOf("=");if(i<=0||i!==j.lastIndexOf("="))throw new Error(`Invalid /sync-audio mapping: ${j.trim()}`);const K=j.slice(0,i).trim(),c=j.slice(i+1).trim();if(!K||!c)throw new Error(`Invalid /sync-audio mapping: ${j.trim()}`);const xe=st(K,"/sync-audio"),B=x[x.length-1];if(B&&xe<=B.video_seconds)throw new Error("/sync-audio video timestamps must be strictly increasing");x.push({video_seconds:xe,...Eb(c)})}return{asset_id:b,anchors:x}}function _b(f){const k=f.asset_id;if(typeof k!="string"||!k.trim())throw new Error("Trim command requires an asset ID");const g=we(k.trim());let b,I,x,j;const i=f.trim_start!==void 0?f.trim_start:f.start;i!=null&&i!==""&&(typeof i=="number"?b=i:typeof i=="string"&&(b=st(i,"/trim")));const K=f.trim_end!==void 0?f.trim_end:f.end;if(K!=null&&K!==""&&(typeof K=="number"?I=K:typeof K=="string"&&(I=st(K,"/trim"))),f.cut_start!==void 0&&f.cut_start!==null&&f.cut_start!==""&&(typeof f.cut_start=="number"?x=f.cut_start:typeof f.cut_start=="string"&&(x=st(f.cut_start,"/trim"))),f.cut_end!==void 0&&f.cut_end!==null&&f.cut_end!==""&&(typeof f.cut_end=="number"?j=f.cut_end:typeof f.cut_end=="string"&&(j=st(f.cut_end,"/trim"))),b!==void 0&&(!Number.isFinite(b)||b<0))throw new Error("trim_start must be >= 0");if(I!==void 0&&(!Number.isFinite(I)||I<0))throw new Error("trim_end must be >= 0");if(b!==void 0&&I!==void 0&&b>=I)throw new Error("trim_start must be less than trim_end");if(x!==void 0&&(!Number.isFinite(x)||x<0))throw new Error("cut_start must be >= 0");if(j!==void 0&&(!Number.isFinite(j)||j<0))throw new Error("cut_end must be >= 0");if(x!==void 0&&j!==void 0&&x>=j)throw new Error("cut_start must be less than cut_end");return{asset_id:g,...b!==void 0&&{trim_start:b},...I!==void 0&&{trim_end:I},...x!==void 0&&{cut_start:x},...j!==void 0&&{cut_end:j}}}function Rb(f){const k=f.asset_id;if(typeof k!="string"||!k.trim())throw new Error("/apply-cuts requires a video cell or asset");const g=we(k.trim()),b=f.cuts;if(!b)throw new Error("/apply-cuts requires at least one cut range");const I=Array.isArray(b)?b:[b];if(I.length===0)throw new Error("/apply-cuts requires at least one cut range");const x=[];for(const j of I){if(typeof j=="object"&&j!==null&&"cut_start"in j&&"cut_end"in j){const J=Number(j.cut_start),Ee=Number(j.cut_end);if(!Number.isFinite(J)||!Number.isFinite(Ee)||J>=Ee||J<0)throw new Error(`Invalid cut range object: ${JSON.stringify(j)}`);x.push({cut_start:J,cut_end:Ee});continue}if(typeof j!="string")throw new Error(`/apply-cuts range must be string or object, got: ${typeof j}`);const i=j.trim(),K=i.indexOf("-");if(K<=0||K===i.length-1)throw new Error(`Invalid /apply-cuts range format: ${i}. Expected <start>-<end>`);const c=i.slice(0,K),xe=i.slice(K+1),B=st(c,"/apply-cuts"),Je=st(xe,"/apply-cuts");if(B>=Je)throw new Error(`/apply-cuts start (${c}) must be before end (${xe})`);x.push({cut_start:B,cut_end:Je})}return{asset_id:g,cuts:x}}function Pb(f){const k=f.asset_id;if(typeof k!="string"||!k.trim())throw new Error("/translate-subs requires an asset ID");const g=we(k.trim()),b=f.language!==void 0?f.language:f.target_language;if(typeof b!="string"||!b.trim())throw new Error("/translate-subs requires a target language code");const I=b.trim().toLowerCase();if(!/^[a-z]{2}$/.test(I))throw new Error("/translate-subs target language must be a two-letter ISO code (e.g. es, fr, de)");return{asset_id:g,language:I}}const ql=new RegExp(`^@?${Yl}$`,"iu"),Mb=new Set(["ig","tiktok","youtube"]),Nl=new Set(["normal","line","dsj","bubble","func"]),Tb=new Set(["landscape","portrait","square"]),jb=/^(?:vid|img|aud|asset|final|script)-[a-z0-9-]+$/i,$b=/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;function qb(f){const k={...f},g=typeof f.platform=="string"?f.platform.trim():"",b=typeof f.custom_prompt=="string"?f.custom_prompt.trim():"",I=g.toLowerCase();if(I&&Mb.has(I))return k.platform=I,b?k.custom_prompt=b:delete k.custom_prompt,k;delete k.platform;const x=[g,b].filter(Boolean).join(" ");return x?k.custom_prompt=x:delete k.custom_prompt,k}function Nb(f){const k={...f},g=typeof f.value=="string"?f.value.trim():"",b=typeof f.style=="string"?f.style.trim():"";if(!g&&!b)return k;const I=b.split(/\s+/).filter(Boolean),x=I[I.length-1]?.toLowerCase()??"";return I.length===1&&Nl.has(x)?(k.style=x,g&&(k.value=g),k):I.length>1&&Nl.has(x)?(k.style=x,k.value=[g,I.slice(0,-1).join(" ")].filter(Boolean).join(" "),k):(delete k.style,k.value=[g,b].filter(Boolean).join(" "),k)}function Lb(f){const k=we(f);return f.startsWith("@")||eb(k)||$b.test(k)||jb.test(k)}function Fb(f){const k=f.trim().split(/\s+/).filter(Boolean);if(k.length===0)return{};const[g,...b]=k;return g&&Lb(g)?{asset_ref:we(g),...b.length>0?{text:b.join(" ")}:{}}:{text:k.join(" ")}}const Db={qr_outro:f=>{const k=f.inputs;if(!Array.isArray(k)||!k.every(b=>typeof b=="string"))throw new Error("/outroqr inputs are required");const g={...f};return delete g.inputs,{...g,...yb(k)}},keywords:f=>{const k=wb(f),g={...f};return delete g.inputs,{...g,...k}},change_speed:f=>{const k={...f};if(!("speed"in k))return k;const g=k.speed;delete k.speed;const b=typeof g=="number"?String(g):typeof g=="string"?g.trim():"",I="Usage: /speed @asset <0.25-4 or 8.32s>";if(!b)throw new Error(I);if(/s$/i.test(b)){const j=Number(b.slice(0,-1));if(!Number.isFinite(j)||j<=0)throw new Error(I);return k.target_duration_seconds=j,k}const x=Number(b.replace(/x$/i,""));if(!Number.isFinite(x))throw new Error(I);return k.speed=x,k},duplicate:f=>{const k={...f},g=typeof f.new_name=="string"?f.new_name.trim():"",b=typeof f.destination=="string"?f.destination.trim():"";if(delete k.new_name,delete k.destination,ql.test(b))return k.destination=we(b).toLowerCase(),g&&(k.new_name=gr(g)),k;const I=[...g.split(/\s+/),b].filter(Boolean),x=I.filter(j=>ql.test(j));if(x.length>1)throw new Error("Usage: /duplicate @asset [@cell] [name]");if(x.length===1){k.destination=we(x[0]).toLowerCase();const j=I.filter(i=>i!==x[0]).join(" ");return j&&(k.new_name=gr(j)),k}return I.length>0&&(k.new_name=gr(I.join(" "))),k},timewarp:f=>{const k=Cb(f),g={...f};return delete g.range,delete g.factor,{...g,...k}},sync_audio:f=>{const k=Ab(f),g={...f};return delete g.mappings,{...g,...k}},apply_sfx:f=>{const k=Ib(f),g={...f};return delete g.timestamp,delete g.type,delete g.description,{...g,...k}},rewrite_script:f=>qb(f),qrbtf:f=>Nb(f),trim:f=>{const k=_b(f),g={...f};return delete g.start,delete g.end,{...g,...k}},apply_cuts:f=>{const k=Rb(f),g={...f};return delete g.cuts,{...g,...k}},translate_subtitles:f=>{const k=Pb(f),g={...f};return delete g.target_language,{...g,...k}}};function Ll(f){const k=f.orientation;if(typeof k!="string")return f;const g=k.trim().toLowerCase();if(!g){const b={...f};return delete b.orientation,b}if(!Tb.has(g))throw new Error("Orientation must be landscape, portrait, or square");return k===g?f:{...f,orientation:g}}function Ob(f,k){if(!f)return Ll(k);const g=Db[f];if(!g)throw new Error(`Unknown command adapter: ${f}`);return Ll(g(k))}const Vb=new Set(["target_duration_seconds","transition_seconds","overlap","timestamp","start","duration"]);function Gb(f,k){const g=we(f),I=(Vb.has(k)?/^(\d+(?:\.\d+)?)(?:s|sec|secs|second|seconds)$/i.exec(g):null)??(k==="boost"?/^(\d+(?:\.\d+)?)x$/i.exec(g):null)??(k==="volume"?/^(\d+(?:\.\d+)?)%$/i.exec(g):null),x=Number(I?.[1]??g);return Number.isFinite(x)?x:g}function Zl(f){const k=we(f).toLowerCase();return["true","1","yes","y","on"].includes(k)?!0:["false","0","no","n","off"].includes(k)?!1:we(f)}function Ub(f,k){if(k.type==="number")return Gb(f,k.name);if(k.type==="boolean"){const g=Zl(f);if(typeof g!="boolean")throw new Error(`${k.name} must be on or off`);return g}return we(f)}function Fl(f,k){if(k.type!=="boolean")return null;const g=we(f).toLowerCase();return g===k.name.toLowerCase()||["true","yes","y","on"].includes(g)?!0:["false","no","n","off"].includes(g)?!1:null}function mt(f,k){if(!f||k.length===0)return{};const g=f.split(/\s+/).filter(i=>i.length>0),b={},I=[];for(const i of g){const K=k.find(c=>c.type==="boolean"&&!(c.name in b)&&Fl(i,c)!==null);if(K){b[K.name]=Fl(i,K);continue}I.push(i)}const x=k[k.length-1];let j=I.length;if(x?.type==="boolean"&&I.length>1&&I.length<k.length){const i=Zl(I[I.length-1]);typeof i=="boolean"&&(b[x.name]=i,j-=1)}for(let i=0;i<k.length&&!(i>=j);i++){const K=k[i];if(K.name in b)continue;const c=i===k.length-1;if(c&&K.type==="string[]")b[K.name]=I.slice(i,j).map(we);else if((c||K.consumeRest)&&K.type==="string"){let xe=I.slice(i,j);if(K.name==="new_name"&&xe.length>1&&xe[0]==="to"&&(xe=xe.slice(1)),b[K.name]=gr(we(xe.join(" "))),K.consumeRest)break}else b[K.name]=Ub(I[i],K)}return b}function Dl(f,k,g){const b=k.toLowerCase(),I=f.filter(c=>c.command.toLowerCase()===b),x=I.length>0?I:f.filter(c=>c.aliases?.some(xe=>xe.toLowerCase()===b));if(x.length<=1)return x[0];const j=g.split(/\s+/).find(Boolean)??"",i=c=>c.params[0]?.name??"",K=c=>/asset|ref|source/.test(i(c));return j.startsWith("@")?x.find(K)??x[0]:x.find(c=>!K(c))??x[0]}const Wb=m.lazy(async()=>({default:(await Us(()=>import("./confirm-bodies-Ds1HtaGc.js").then(k=>k.W),__vite__mapDeps([0,1,2,3,4,5,6,7,8,9,10,11,12]))).WatermarkBody})),Ol=m.lazy(async()=>({default:(await Us(()=>import("./music-video-CWtxPlxq.js"),__vite__mapDeps([13,1,2,3,4,5,6,7,8,9,10,11,14]))).MusicVideoEditor})),zb=m.lazy(async()=>({default:(await Us(()=>import("./alive-captions-Bp6dxosy.js"),__vite__mapDeps([15,1,6,2,3,4,5,8,16]))).AliveCaptionsStudio}));function Bb(f){return{mode:f.mode,reference:f.reference,referenceStartSeconds:f.startSeconds,referenceDurationSeconds:f.durationSeconds}}const Vl="videobook.cloud-generation-consent";function ur(f){return window.localStorage.getItem(Vl)==="accepted"?!0:window.confirm(`Cloud generation disclosure
|
|
1
|
+
const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["assets/confirm-bodies-BxWXwDf0.js","assets/vendor-react-Dj7D1fD4.js","assets/videobook-CsW453sb.js","assets/vendor-D8XcMav4.js","assets/vendor-mcp-D_C3EZPv.js","assets/vendor-D2rfiZ5j.css","assets/vendor-remotion-CH1HXrlc.js","assets/ui-z5r-p0K9.js","assets/vendor-icons-CGqhCIXV.js","assets/vendor-flow-nqTFQmTh.js","assets/vendor-flow-BnuhLJ6X.css","assets/ui-mq0uIS5P.css","assets/confirm-bodies-DrMhaXC6.css","assets/music-video-CT4C55ok.js","assets/music-video-DPaiKKEq.css","assets/alive-captions-Cj8C1tCN.js","assets/alive-captions-BWb5nLKj.css"])))=>i.map(i=>d[i]);
|
|
2
|
+
import{a as m,j as C,d as gf}from"./vendor-react-Dj7D1fD4.js";import{i as kf,S as bf,b as ji,c as wf}from"./vendor-flow-nqTFQmTh.js";import{g as Us}from"./vendor-mcp-D_C3EZPv.js";import{z as ot,E as nt,F as hf,r as $i,H as vf,J as yf,K as If,L as Cf,O as Sf,T as xf,Q as Ef,U as Af,W as _f,o as Rf,X as Pf,p as Mf,m as Tf,n as jf,Y as $f,Z as qf,_ as Nf,$ as Lf,a0 as Ff,a1 as Df,a2 as Of,a3 as qi,q as Vf,a4 as Gf,a5 as Uf,a6 as Wf}from"./ui-z5r-p0K9.js";import{ew as zf,ex as Hf,ey as Ni,ez as Li,eA as Is,eB as Bf,cF as Zn,eC as Kf,eD as Jf,eE as Xf,eF as Qf,eG as Yf,eH as Zf,eI as em,bI as _,bU as ie,eJ as tm,eK as Fi,eL as to,eM as om,cM as Di,eN as Oi,eO as nm,dq as rm,dt as sm,eP as Cs,eQ as am,eR as im,eS as lm,eT as cm,eU as Vi,eV as dm,eW as um,eX as fm,a as mm,eY as pm,eZ as gm,e_ as km,e$ as bm,f0 as wm,bK as D,cs as Gi,f1 as hm,f2 as vm,f3 as ym,f4 as Im,f5 as Nt,f6 as Cm,f7 as Sm,f8 as xm,f9 as Ui,fa as ft,fb as L,fc as M,fd as Ss,fe as Wi,ff as Em,fg as Am,fh as _m,fi as ge,fj as oo,fk as zi,fl as Rm,fm as Pm,fn as Mm,fo as Lt,fp as Tm,fq as jm,bB as Ft,fr as $m,fs as Hi,ft as er,fu as qm,fv as Nm,fw as Bi,fx as Lm,fy as Fm,fz as Dm,fA as Ki,fB as Om,fC as Vm,fD as Gm,fE as pn,fF as Um,fG as Ji,fH as Wm,dC as zm,fI as tr,dD as Hm,dE as Bm,fJ as Xi,fK as Km,fL as xs,fM as Jm,fN as Xm,fO as Qm,fP as Ym,df as Zm,bS as ep,fQ as St,a8 as gn,fR as tp,fS as op,fT as np,di as Qi,fU as rp,fV as Yi,fW as Zi,fX as Ke,fY as sp,fZ as ap,O as ip,f_ as lp,f$ as cp,g0 as dp,g1 as el,g2 as Es,g3 as tl,g4 as As,g5 as or,g6 as up,g7 as fp,g8 as mp,g9 as pp,ga as gp,gb as ol,gc as kp,gd as bp,dP as nr,bD as wp,bC as hp,dB as vp,ge as yp,gf as Ip,gg as Cp,gh as nl,gi as Sp,gj as xp,gk as Ep,gl as rl,gm as Ap,cp as _p,cq as Rp,am as Pp,cn as sl,gn as al,c2 as Mp,ct as Tp,go as jp,gp as $p,gq as _s,gr as qp,gs as Np,b8 as il,gt as Rs,gu as Mo,bL as Ps,bG as no,a9 as Lp,gv as ll,gw as Fp,gx as Ms,gy as Dp,gz as ro,gA as Op,gB as Vp,gC as Gp,gD as Up,gE as Wp,gF as zp,gG as Ql,gH as Ts,gI as cl,gJ as Hp,gK as Bp,gL as Kp,gM as Jp,c7 as js,gN as dl,gO as Xp,gP as Qp,gQ as Yp,gR as Zp,gS as eg,gT as tg,gU as og,gV as ng,gW as ul,bZ as Dt,gX as rg,gY as sg,gZ as fl,aa as ml,b1 as ag,g_ as ig,bt as lg,g$ as cg,dh as dg,h0 as ug,h1 as fg,h2 as mg,h3 as pl,h4 as pg,h5 as gg,h6 as kg,h7 as rr,h8 as bg,h9 as $s,ha as wg,aL as hg,hb as vg,aJ as yg,hc as Ig,hd as Cg,he as qs,hf as Sg,hg as xg,hh as gl,hi as Eg,hj as kl,d7 as Ag,hk as bl,hl as _g,hm as Ns,hn as Rg,ho as sr,hp as Pg,hq as Mg,hr as Tg,hs as jg,ht as $g,hu as qg,hv as Ng,b0 as Lg,aH as Fg,hw as Dg,hx as Og,hy as Vg,hz as Gg,dk as wl,hA as Ug,hB as hl,hC as kn,hD as ar,hE as Wg,hF as zg,hG as Hg,hH as Bg,hI as Kg,hJ as Jg,hK as Xg,hL as Qg,hM as Yg,hN as Zg,hO as vl,hP as ek,hQ as yl,hR as tk,hS as ok,hT as ir,hU as nk,hV as rk,hW as sk,hX as ak,hY as ik,hZ as lk,h_ as Il,h$ as ck,i0 as dk,i1 as uk,i2 as Cl,i3 as fk,i4 as Sl,i5 as mk,i6 as xl,i7 as pk,i8 as El,i9 as lr,ia as Al,ib as cr,ic as _l,d8 as gk,id as kk,N as bk,D as wk,ie as hk,ig as Ls,ih as vk,ii as yk,ij as Ik,ik as Ck,il as Sk,im as xk,io as Ek,ip as Ak,iq as _k,ir as Rk,is as Rl,it as Pk,iu as Mk,iv as Tk,iw as jk,ix as $k,iy as qk,iz as Nk,iA as Pl,iB as Po,iC as Lk,iD as Fk,Y as Dk,iE as Ok,iF as Vk,iG as Gk,iH as bn,iI as Uk,iJ as Wk,iK as zk,iL as Hk,iM as Bk,iN as Kk}from"./videobook-CsW453sb.js";import{a as Jk,T as Xk,G as Qk,P as Yk,C as Zk,S as eb,b as tb,R as Ml,N as ob}from"./confirm-bodies-BxWXwDf0.js";import{i as nb,A as Yl,n as Se,b as W,m as Tl,v as jl,x as dr,y as xt,Y as rb,f as pr,s as sb}from"./vendor-D8XcMav4.js";import{J as ab}from"./jobs-ui-BudI4w0r.js";import{N as ib}from"./inspector-BC6xWkJU.js";import{N as lb}from"./fullscreen-DyEncSdm.js";import{G as cb,a as db,b as ub,c as fb}from"./goal-ui-BdFeoSWh.js";import{ar as mb,z as $l,H as pb,B as gb,at as kb,a8 as bb,b as wb,au as hb}from"./vendor-icons-CGqhCIXV.js";import"./vendor-remotion-CH1HXrlc.js";(function(){const k=document.createElement("link").relList;if(k&&k.supports&&k.supports("modulepreload"))return;for(const I of document.querySelectorAll('link[rel="modulepreload"]'))b(I);new MutationObserver(I=>{for(const x of I)if(x.type==="childList")for(const j of x.addedNodes)j.tagName==="LINK"&&j.rel==="modulepreload"&&b(j)}).observe(document,{childList:!0,subtree:!0});function g(I){const x={};return I.integrity&&(x.integrity=I.integrity),I.referrerPolicy&&(x.referrerPolicy=I.referrerPolicy),I.crossOrigin==="use-credentials"?x.credentials="include":I.crossOrigin==="anonymous"?x.credentials="omit":x.credentials="same-origin",x}function b(I){if(I.ep)return;I.ep=!0;const x=g(I);fetch(I.href,x)}})();const we=f=>f.startsWith("@")?f.slice(1):f;function gr(f){const k=f.trim();if(k.length<2)return k;const g=k[0],b=k[k.length-1];return(g==='"'||g==="'")&&g===b?k.slice(1,-1).trim():k}const vb=/^[a-z0-9][a-z0-9-]*$/i;function yb(f){const k=f.asset_id;if(typeof k!="string"||!k.trim())throw new Error("/keywords requires a video cell or asset");const g=we(k.trim()),b=f.inputs;if(b===void 0)return{asset_id:g};if(!Array.isArray(b)||!b.every(j=>typeof j=="string"))throw new Error("/keywords inputs must be words");const I=b.map(j=>j.trim()).filter(Boolean);if(I.length===0)return{asset_id:g};const x=Ib(I);return x?{asset_id:g,...x}:{asset_id:g,keywords:I}}function Ib(f){const k=f[0]?.toLowerCase()??"",g=f.slice(1);if(["off","false","no","0"].includes(k))return g.length===0?{enabled:!1}:null;if(!["on","true","yes","1"].includes(k)||g.length>2)return null;if(g.length===0)return{enabled:!0};const b=Number(g[0]);if(!Number.isInteger(b)||b<1||b>20)return null;if(g.length===1)return{enabled:!0,max_keywords:b};const I=Number(g[1]);return!Number.isFinite(I)||I<.8||I>5?null:{enabled:!0,max_keywords:b,linger_seconds:I}}function Cb(f){const k=f.toLowerCase();return k==="16:9"||k==="landscape"?"16:9":k==="9:16"||k==="portrait"?"9:16":k==="1:1"||k==="square"?"1:1":null}function Sb(f){const k=f.map(we),g=[];let b;for(const I of k){const x=Cb(I);if(x){if(b)throw new Error("/outroqr accepts only one aspect ratio");b=x;continue}if(!vb.test(I))throw new Error(`Unrecognized /outroqr input: ${I}`);if(g.push(I),g.length>4)throw new Error("/outroqr accepts at most 4 QR images")}if(g.length===0)throw new Error("/outroqr requires at least one QR image cell or asset");return{qr_image_refs:g,...b?{aspect_ratio:b}:{}}}function xb(f){const k=f.asset_id,g=f.timestamp,b=f.type,I=f.description;if(typeof k!="string"||!k.trim())throw new Error("/apply-sfx requires a video cell or asset");const x=we(k.trim());if(typeof g!="string"&&typeof g!="number")throw new Error("/apply-sfx requires a timestamp");const j=typeof g=="number"?g:st(g,"/apply-sfx");if(!Number.isFinite(j)||j<0)throw new Error("/apply-sfx timestamp must be 0 or later");if(typeof b!="string"||!b.trim())throw new Error("/apply-sfx requires an effect type");if(typeof I!="string"||!I.trim())throw new Error("/apply-sfx requires an effect description");return{asset_id:x,sfx:[{timestamp:j,type:b.trim(),description:I.trim()}]}}function st(f,k){const b=f.trim().replace(/s$/i,"").split(":");if(b.length===1){const x=Number(b[0]);if(Number.isFinite(x)&&x>=0)return x;throw new Error(`Invalid ${k} timestamp: ${f}`)}if(b.length!==2&&b.length!==3)throw new Error(`Invalid ${k} timestamp: ${f}`);if(!b.every(x=>/^\d+(?:\.\d+)?$/.test(x)))throw new Error(`Invalid ${k} timestamp: ${f}`);const I=b.map(Number);return b.length===2?I[0]*60+I[1]:I[0]*3600+I[1]*60+I[2]}function Eb(f){const k=f.asset_id,g=f.range,b=f.factor;if(typeof k!="string"||!k.trim())throw new Error("/timewarp requires a video cell or asset");const I=we(k.trim());if(typeof g!="string")throw new Error("/timewarp requires a <start>-<end> range");const x=/^(.+)-(.+)$/.exec(g.trim());if(!x)throw new Error("/timewarp requires a <start>-<end> range");const j=st(x[1],"/timewarp"),i=st(x[2],"/timewarp");if(j>=i)throw new Error("/timewarp start must be before end");if(typeof b!="string"&&typeof b!="number")throw new Error("/timewarp requires a stretch factor");const K=String(b).trim();if(!/^\d+(?:\.\d+)?x?$/i.test(K))throw new Error(`Invalid /timewarp stretch factor: ${K}`);const c=Number(K.replace(/x$/i,""));if(!Number.isFinite(c)||c<.25||c>4)throw new Error("/timewarp stretch factor must be between 0.25x and 4x");if(c===1)throw new Error("/timewarp stretch factor 1x is a no-op");return{asset_id:I,start_seconds:j,end_seconds:i,stretch_factor:c}}function Ab(f){const k=f.trim(),g=k[0],b=k[k.length-1],I=g==='"'||g==="'";if(I||(b==='"'||b==="'")){if(!I||g!==b||k.length<2)throw new Error(`/sync-audio has mismatched quotes: ${f}`);return k.slice(1,-1).trim()}return k}function _b(f){const g=f.trim().replace(/s$/i,"").split(":");return g.length<1||g.length>3?!1:g.every(b=>/^\d+(?:\.\d+)?$/.test(b))}function Rb(f){const k=f.trim(),g=k.startsWith('"')||k.startsWith("'"),b=Ab(f);if(!b)throw new Error("/sync-audio anchor target cannot be empty");return!g&&_b(b)?{audio_seconds:st(b,"/sync-audio")}:{audio_cue:b}}function Pb(f){const k=f.asset_id,g=f.mappings;if(typeof k!="string"||!k.trim())throw new Error("/sync-audio requires a video cell or asset");const b=we(k.trim());if(typeof g!="string"||!g.trim())throw new Error("/sync-audio requires at least one video-time=audio-target mapping");const I=g.split(";"),x=[];for(const j of I){const i=j.indexOf("=");if(i<=0||i!==j.lastIndexOf("="))throw new Error(`Invalid /sync-audio mapping: ${j.trim()}`);const K=j.slice(0,i).trim(),c=j.slice(i+1).trim();if(!K||!c)throw new Error(`Invalid /sync-audio mapping: ${j.trim()}`);const xe=st(K,"/sync-audio"),H=x[x.length-1];if(H&&xe<=H.video_seconds)throw new Error("/sync-audio video timestamps must be strictly increasing");x.push({video_seconds:xe,...Rb(c)})}return{asset_id:b,anchors:x}}function Mb(f){const k=f.asset_id;if(typeof k!="string"||!k.trim())throw new Error("Trim command requires an asset ID");const g=we(k.trim());let b,I,x,j;const i=f.trim_start!==void 0?f.trim_start:f.start;i!=null&&i!==""&&(typeof i=="number"?b=i:typeof i=="string"&&(b=st(i,"/trim")));const K=f.trim_end!==void 0?f.trim_end:f.end;if(K!=null&&K!==""&&(typeof K=="number"?I=K:typeof K=="string"&&(I=st(K,"/trim"))),f.cut_start!==void 0&&f.cut_start!==null&&f.cut_start!==""&&(typeof f.cut_start=="number"?x=f.cut_start:typeof f.cut_start=="string"&&(x=st(f.cut_start,"/trim"))),f.cut_end!==void 0&&f.cut_end!==null&&f.cut_end!==""&&(typeof f.cut_end=="number"?j=f.cut_end:typeof f.cut_end=="string"&&(j=st(f.cut_end,"/trim"))),b!==void 0&&(!Number.isFinite(b)||b<0))throw new Error("trim_start must be >= 0");if(I!==void 0&&(!Number.isFinite(I)||I<0))throw new Error("trim_end must be >= 0");if(b!==void 0&&I!==void 0&&b>=I)throw new Error("trim_start must be less than trim_end");if(x!==void 0&&(!Number.isFinite(x)||x<0))throw new Error("cut_start must be >= 0");if(j!==void 0&&(!Number.isFinite(j)||j<0))throw new Error("cut_end must be >= 0");if(x!==void 0&&j!==void 0&&x>=j)throw new Error("cut_start must be less than cut_end");return{asset_id:g,...b!==void 0&&{trim_start:b},...I!==void 0&&{trim_end:I},...x!==void 0&&{cut_start:x},...j!==void 0&&{cut_end:j}}}function Tb(f){const k=f.asset_id;if(typeof k!="string"||!k.trim())throw new Error("/apply-cuts requires a video cell or asset");const g=we(k.trim()),b=f.cuts;if(!b)throw new Error("/apply-cuts requires at least one cut range");const I=Array.isArray(b)?b:[b];if(I.length===0)throw new Error("/apply-cuts requires at least one cut range");const x=[];for(const j of I){if(typeof j=="object"&&j!==null&&"cut_start"in j&&"cut_end"in j){const J=Number(j.cut_start),Ee=Number(j.cut_end);if(!Number.isFinite(J)||!Number.isFinite(Ee)||J>=Ee||J<0)throw new Error(`Invalid cut range object: ${JSON.stringify(j)}`);x.push({cut_start:J,cut_end:Ee});continue}if(typeof j!="string")throw new Error(`/apply-cuts range must be string or object, got: ${typeof j}`);const i=j.trim(),K=i.indexOf("-");if(K<=0||K===i.length-1)throw new Error(`Invalid /apply-cuts range format: ${i}. Expected <start>-<end>`);const c=i.slice(0,K),xe=i.slice(K+1),H=st(c,"/apply-cuts"),Je=st(xe,"/apply-cuts");if(H>=Je)throw new Error(`/apply-cuts start (${c}) must be before end (${xe})`);x.push({cut_start:H,cut_end:Je})}return{asset_id:g,cuts:x}}function jb(f){const k=f.asset_id;if(typeof k!="string"||!k.trim())throw new Error("/translate-subs requires an asset ID");const g=we(k.trim()),b=f.language!==void 0?f.language:f.target_language;if(typeof b!="string"||!b.trim())throw new Error("/translate-subs requires a target language code");const I=b.trim().toLowerCase();if(!/^[a-z]{2}$/.test(I))throw new Error("/translate-subs target language must be a two-letter ISO code (e.g. es, fr, de)");return{asset_id:g,language:I}}const ql=new RegExp(`^@?${Yl}$`,"iu"),$b=new Set(["ig","tiktok","youtube"]),Nl=new Set(["normal","line","dsj","bubble","func"]),qb=new Set(["landscape","portrait","square"]),Nb=/^(?:vid|img|aud|asset|final|script)-[a-z0-9-]+$/i,Lb=/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;function Fb(f){const k={...f},g=typeof f.platform=="string"?f.platform.trim():"",b=typeof f.custom_prompt=="string"?f.custom_prompt.trim():"",I=g.toLowerCase();if(I&&$b.has(I))return k.platform=I,b?k.custom_prompt=b:delete k.custom_prompt,k;delete k.platform;const x=[g,b].filter(Boolean).join(" ");return x?k.custom_prompt=x:delete k.custom_prompt,k}function Db(f){const k={...f},g=typeof f.value=="string"?f.value.trim():"",b=typeof f.style=="string"?f.style.trim():"";if(!g&&!b)return k;const I=b.split(/\s+/).filter(Boolean),x=I[I.length-1]?.toLowerCase()??"";return I.length===1&&Nl.has(x)?(k.style=x,g&&(k.value=g),k):I.length>1&&Nl.has(x)?(k.style=x,k.value=[g,I.slice(0,-1).join(" ")].filter(Boolean).join(" "),k):(delete k.style,k.value=[g,b].filter(Boolean).join(" "),k)}function Ob(f){const k=we(f);return f.startsWith("@")||nb(k)||Lb.test(k)||Nb.test(k)}function Vb(f){const k=f.trim().split(/\s+/).filter(Boolean);if(k.length===0)return{};const[g,...b]=k;return g&&Ob(g)?{asset_ref:we(g),...b.length>0?{text:b.join(" ")}:{}}:{text:k.join(" ")}}const Gb={qr_outro:f=>{const k=f.inputs;if(!Array.isArray(k)||!k.every(b=>typeof b=="string"))throw new Error("/outroqr inputs are required");const g={...f};return delete g.inputs,{...g,...Sb(k)}},keywords:f=>{const k=yb(f),g={...f};return delete g.inputs,{...g,...k}},change_speed:f=>{const k={...f};if(!("speed"in k))return k;const g=k.speed;delete k.speed;const b=typeof g=="number"?String(g):typeof g=="string"?g.trim():"",I="Usage: /speed @asset <0.25-4 or 8.32s>";if(!b)throw new Error(I);if(/s$/i.test(b)){const j=Number(b.slice(0,-1));if(!Number.isFinite(j)||j<=0)throw new Error(I);return k.target_duration_seconds=j,k}const x=Number(b.replace(/x$/i,""));if(!Number.isFinite(x))throw new Error(I);return k.speed=x,k},duplicate:f=>{const k={...f},g=typeof f.new_name=="string"?f.new_name.trim():"",b=typeof f.destination=="string"?f.destination.trim():"";if(delete k.new_name,delete k.destination,ql.test(b))return k.destination=we(b).toLowerCase(),g&&(k.new_name=gr(g)),k;const I=[...g.split(/\s+/),b].filter(Boolean),x=I.filter(j=>ql.test(j));if(x.length>1)throw new Error("Usage: /duplicate @asset [@cell] [name]");if(x.length===1){k.destination=we(x[0]).toLowerCase();const j=I.filter(i=>i!==x[0]).join(" ");return j&&(k.new_name=gr(j)),k}return I.length>0&&(k.new_name=gr(I.join(" "))),k},timewarp:f=>{const k=Eb(f),g={...f};return delete g.range,delete g.factor,{...g,...k}},sync_audio:f=>{const k=Pb(f),g={...f};return delete g.mappings,{...g,...k}},apply_sfx:f=>{const k=xb(f),g={...f};return delete g.timestamp,delete g.type,delete g.description,{...g,...k}},rewrite_script:f=>Fb(f),qrbtf:f=>Db(f),trim:f=>{const k=Mb(f),g={...f};return delete g.start,delete g.end,{...g,...k}},apply_cuts:f=>{const k=Tb(f),g={...f};return delete g.cuts,{...g,...k}},translate_subtitles:f=>{const k=jb(f),g={...f};return delete g.target_language,{...g,...k}}};function Ll(f){const k=f.orientation;if(typeof k!="string")return f;const g=k.trim().toLowerCase();if(!g){const b={...f};return delete b.orientation,b}if(!qb.has(g))throw new Error("Orientation must be landscape, portrait, or square");return k===g?f:{...f,orientation:g}}function Ub(f,k){if(!f)return Ll(k);const g=Gb[f];if(!g)throw new Error(`Unknown command adapter: ${f}`);return Ll(g(k))}const Wb=new Set(["target_duration_seconds","transition_seconds","overlap","timestamp","start","duration"]);function zb(f,k){const g=we(f),I=(Wb.has(k)?/^(\d+(?:\.\d+)?)(?:s|sec|secs|second|seconds)$/i.exec(g):null)??(k==="boost"?/^(\d+(?:\.\d+)?)x$/i.exec(g):null)??(k==="volume"?/^(\d+(?:\.\d+)?)%$/i.exec(g):null),x=Number(I?.[1]??g);return Number.isFinite(x)?x:g}function Zl(f){const k=we(f).toLowerCase();return["true","1","yes","y","on"].includes(k)?!0:["false","0","no","n","off"].includes(k)?!1:we(f)}function Hb(f,k){if(k.type==="number")return zb(f,k.name);if(k.type==="boolean"){const g=Zl(f);if(typeof g!="boolean")throw new Error(`${k.name} must be on or off`);return g}return we(f)}function Fl(f,k){if(k.type!=="boolean")return null;const g=we(f).toLowerCase();return g===k.name.toLowerCase()||["true","yes","y","on"].includes(g)?!0:["false","no","n","off"].includes(g)?!1:null}function mt(f,k){if(!f||k.length===0)return{};const g=f.split(/\s+/).filter(i=>i.length>0),b={},I=[];for(const i of g){const K=k.find(c=>c.type==="boolean"&&!(c.name in b)&&Fl(i,c)!==null);if(K){b[K.name]=Fl(i,K);continue}I.push(i)}const x=k[k.length-1];let j=I.length;if(x?.type==="boolean"&&I.length>1&&I.length<k.length){const i=Zl(I[I.length-1]);typeof i=="boolean"&&(b[x.name]=i,j-=1)}for(let i=0;i<k.length&&!(i>=j);i++){const K=k[i];if(K.name in b)continue;const c=i===k.length-1;if(c&&K.type==="string[]")b[K.name]=I.slice(i,j).map(we);else if((c||K.consumeRest)&&K.type==="string"){let xe=I.slice(i,j);if(K.name==="new_name"&&xe.length>1&&xe[0]==="to"&&(xe=xe.slice(1)),b[K.name]=gr(we(xe.join(" "))),K.consumeRest)break}else b[K.name]=Hb(I[i],K)}return b}function Dl(f,k,g){const b=k.toLowerCase(),I=f.filter(c=>c.command.toLowerCase()===b),x=I.length>0?I:f.filter(c=>c.aliases?.some(xe=>xe.toLowerCase()===b));if(x.length<=1)return x[0];const j=g.split(/\s+/).find(Boolean)??"",i=c=>c.params[0]?.name??"",K=c=>/asset|ref|source/.test(i(c));return j.startsWith("@")?x.find(K)??x[0]:x.find(c=>!K(c))??x[0]}const Bb=m.lazy(async()=>({default:(await Us(()=>import("./confirm-bodies-BxWXwDf0.js").then(k=>k.W),__vite__mapDeps([0,1,2,3,4,5,6,7,8,9,10,11,12]))).WatermarkBody})),Ol=m.lazy(async()=>({default:(await Us(()=>import("./music-video-CT4C55ok.js"),__vite__mapDeps([13,1,2,3,4,5,6,7,8,9,10,11,14]))).MusicVideoEditor})),Kb=m.lazy(async()=>({default:(await Us(()=>import("./alive-captions-Cj8C1tCN.js"),__vite__mapDeps([15,1,6,2,3,4,5,8,16]))).AliveCaptionsStudio}));function Jb(f){return{mode:f.mode,reference:f.reference,referenceStartSeconds:f.startSeconds,referenceDurationSeconds:f.durationSeconds}}const Vl="videobook.cloud-generation-consent";function ur(f){return window.localStorage.getItem(Vl)==="accepted"?!0:window.confirm(`Cloud generation disclosure
|
|
3
3
|
|
|
4
4
|
Provider/model: ${f.provider??"unknown"} · ${f.model??f.tool}
|
|
5
5
|
Payload class: prompt text and connected media references.
|
|
6
6
|
Your local source files are sent only when required by the selected model.
|
|
7
7
|
|
|
8
|
-
Continue and remember this choice on this device?`)?(window.localStorage.setItem(Vl,"accepted"),!0):!1}const Hb=typeof window>"u"?"http://localhost/mcp":new URL("/mcp",window.location.origin).toString(),wn=500,hn=5*6e4,fr=10,Kb=5,Jb=1e3,Xb=2e3,Qb=45*6e4,Gl=5e3,Yb=3e3,Zb=20*6e4,Ul=750,ew=20,Wl=45*6e4,tw=new Set(["queued","running","completing"]),ow=[];function rt(f){return new Promise(k=>window.setTimeout(k,f))}const nw=[{id:"jobs",label:"Jobs",icon:gb},{id:"settings",label:"Settings",icon:kb}];function zl(f,k){return!!(k==="transcript"?f?.transcript:f?.visionAnalysis)}function rw(f){return Vp(f)}function Gs(f){return f==="generate_audio"?"audio":f==="generate_image"?"image":"video"}function Bl(f){const k=f.document.cells.find(g=>g.id===f.sourceCellId);if(!k)throw new Error("The source asset cell is no longer available");return Ql({actions:f.actions,cellId:f.cellId,command:{cellType:f.cellType,mediaKind:Gs(f.cellType),prompt:"",sourceReferences:[W(k.slot)]},document:f.document,fallbackSlot:Mo(f.cellType,f.document.cells,f.lastWorkSlot),lastWorkSlot:f.lastWorkSlot})}function pt(f){return{ok:!0,message:f,nextInput:"/apply",selectInput:!0}}function Hl(f){return{ok:!0,message:f,nextInput:"/apply ",selectInput:!1}}function Kl(f){return f.match(/https?:\/\/[^\s]+/u)?.[0]??f}function vn(f){return{ok:!1,error:f instanceof Error?f.message:String(f)}}function Fs(f,k){const g=Gp(k);if(g.artifactId&&g.artifactId!==f.asset.artifactId)throw new Error("The subject map belongs to another image artifact");if(g.objectHash&&g.objectHash!==f.asset.objectHash)throw new Error("The image changed before subject analysis finished");return{...g,artifactId:g.artifactId??f.asset.artifactId,objectHash:g.objectHash??f.asset.objectHash??null,width:g.width??f.asset.width,height:g.height??f.asset.height}}function Ds(f,k,g=f.subjectMap){return{status:"failed",artifactId:f.asset.artifactId,objectHash:f.asset.objectHash??null,width:f.asset.width,height:f.asset.height,baseUrl:g?.baseUrl??null,jobId:g?.jobId??null,startedAt:g?.startedAt??null,error:k instanceof Error?k.message:String(k),subjects:g?.subjects??[]}}function sw(f,k){if(!f||!k)return null;const g=pr(k),b=f.tracks.filter(I=>I.trackId.toLowerCase().startsWith(g)||I.name.toLowerCase()===g);return b.length===1?b[0]:null}function ec(f,k){const g=f.tracks.filter(I=>I.kind==="audio"&&I.enabled&&!I.locked&&!I.muted);return g.find(I=>{const x=f.clips.filter(j=>j.trackId===I.trackId);return x.length===1&&x[0]?.timelineStartFrame===0&&x[0].source.kind==="timed"&&x[0].source.artifactId===k})??g.find(I=>!f.clips.some(x=>x.trackId===I.trackId))??null}function aw(f,k,g){const b=ec(f,k);if(!b)return!1;const I=f.clips.filter(j=>j.trackId===b.trackId),x=I[0];return I.length===1&&x!==void 0&&x.timelineStartFrame===0&&x.durationFrames===g&&x.source.kind==="timed"&&x.source.artifactId===k}function iw(f,k,g){const b=f.stages.find(i=>i.kind==="edit"),I=b?.intent.operations.find(i=>i.kind==="insert-clip"&&i.placement.source.artifactId===g);if(I?.kind==="insert-clip")return I.placement.durationFrames;const x=k.clips.find(i=>i.timelineStartFrame===0&&i.source.kind==="timed"&&i.source.artifactId===g),j=b?.intent.operations.find(i=>i.kind==="trim-clip"&&i.clipId===x?.clipId);if(j?.kind==="trim-clip")return j.durationFrames;if(x)return x.durationFrames;throw new Error("The soundtrack setup plan has no duration boundary")}function lw(f){const k=f.stages.flatMap(I=>I.kind==="edit"?I.intent.operations:[]),g=k.filter(I=>I.kind==="insert-clip").length,b=k.filter(I=>I.kind==="set-clip-audio"?I.audio.muted:I.kind==="set-clip-speed"&&I.audioPolicy==="mute").length;return`${g>0?"Place":"Normalize"} master soundtrack · mute ${b} other ${b===1?"clip":"clips"}`}function Jl(f){return f.valid?null:f.conflicts.map(g=>g.message).join(" · ")||"The canonical edit preview is invalid"}function cw(f){const g=f.find(b=>b.kind==="edit")?.intent.operations.map(b=>{if(b.kind==="insert-clip")return{kind:"insert",mode:b.mode,artifact_id:b.placement.source.artifactId,track_id:b.placement.trackId,timeline_start_frame:b.placement.timelineStartFrame,duration_frames:b.placement.durationFrames,...b.placement.source.kind==="timed"?{source_start_tick:b.placement.source.range.startTick,source_duration_ticks:b.placement.source.range.durationTicks}:{}};if(b.kind==="trim-clip")return{kind:"trim",clip_id:b.clipId,timeline_start_frame:b.timelineStartFrame,duration_frames:b.durationFrames};if(b.kind==="set-clip-audio")return{kind:"volume",clip_id:b.clipId,gain_db:b.audio.gainDb,muted:b.audio.muted,fade_in_frames:b.audio.fadeInFrames,fade_out_frames:b.audio.fadeOutFrames};if(b.kind==="move-clip")return{kind:"move",clip_id:b.clipId,track_id:b.trackId,timeline_start_frame:b.timelineStartFrame};if(b.kind==="split-clip")return{kind:"split",clip_id:b.clipId,split_frame:b.splitFrame};if(b.kind==="set-clip-transform")return{kind:"transform",clip_id:b.clipId,fit:b.transform.fit,position_x:b.transform.positionX,position_y:b.transform.positionY,scale_x:b.transform.scaleX,scale_y:b.transform.scaleY,rotation_degrees:b.transform.rotationDegrees,opacity:b.transform.opacity,crop_top:b.transform.cropTop,crop_right:b.transform.cropRight,crop_bottom:b.transform.cropBottom,crop_left:b.transform.cropLeft};if(b.kind==="set-clip-speed")return{kind:"speed",clip_id:b.clipId,numerator:b.speed.numerator,denominator:b.speed.denominator,reverse:b.reverse,audio_policy:b.audioPolicy};if(b.kind==="set-transition")return{kind:"transition",outgoing_clip_id:b.outgoingClipId,incoming_clip_id:b.incomingClipId,transition_kind:b.transition?.kind??null,...b.transition?{duration_frames:b.transition.durationFrames,alignment:b.transition.alignment}:{}};if(b.kind==="upsert-caption-cue")return{kind:"caption",cue_id:b.cue.cueId,track_id:b.cue.trackId,timeline_start_frame:b.cue.timelineStartFrame,duration_frames:b.cue.durationFrames,text:b.cue.text,style_id:b.cue.styleId,...b.cue.speaker?{speaker:b.cue.speaker}:{}};throw new Error(`The edit cannot be replanned: ${b.kind}`)})??[];if(g.length===0)throw new Error("The plan has no editable operation");return g.length===1?g[0]:g}function yn(f){try{return window.localStorage.getItem(f)??""}catch{return""}}function Ot(f,k){try{window.localStorage.setItem(f,k)}catch{return}}const mr={offset:0,limit:24,total:0,hasMore:!1};function Os(f){return f==="final"?"video":f==="audio"||f==="image"||f==="video"?f:null}function dw(f){return f==="all"?["audio","image","video","final"]:f==="video"?["video","final"]:[f]}function Vs(f,k){return dw(f).includes(k)}async function Xl(f){const k=await window.crypto.subtle.digest("SHA-256",await f.arrayBuffer());return[...new Uint8Array(k)].map(g=>g.toString(16).padStart(2,"0")).join("")}function uw(f){return`slot-context-menu-${f.row}-${f.column}`}const fw={cell:Nf,timeline:qf,goal:lb},mw={busRiver:$f},pw={hideAttribution:!0},gw={selectable:!1},kw=["Shift","Control","Meta"],bw=[];function ww({initialWorkspace:f}){const k=m.useMemo(()=>Wf(f),[f]),g=zf({url:Hb,clientName:"videobook",reconnectDelayMs:3e3}),[b,I]=m.useState(()=>Ni(window.location.pathname)),[x,j]=m.useState(()=>k?.books??[]),[i,K]=m.useState(()=>k?.bookId??yn("videobook.active-book")),[c,xe]=m.useState(()=>k?.notebook??null),[B,Je]=m.useState(()=>k?.assets??[]),[J,Ee]=m.useState(()=>k?.sequence??null),[Ve,Ws]=m.useState(()=>k?.jobs??[]),[tc,zs]=m.useState(()=>Date.now()),[In,oc]=m.useState(()=>k?.commands??[]),[Et,kr]=m.useState([]),[br,wr]=m.useState({loading:!1,error:null}),[qe,Xe]=m.useState(null),at=m.useRef(0),To=m.useRef(0),[hr,gt]=m.useState(null),[Cn,Vt]=m.useState(null),[nc,rc]=m.useState(null),[sc,ac]=m.useState(null),[Ne,jo]=m.useState(null),Bs=m.useRef(null),[vr,ic]=m.useState(()=>k?.chatModelCatalog??Li),[Hs,Ks]=m.useState(()=>Is(k?.chatModelCatalog??Li,yn("videobook.chat-model"))),[Qe,Js]=m.useState(()=>k?.generationActions??[]),lc=m.useMemo(()=>new Map(Qe.map(e=>[e.model,e.title])),[Qe]),[cc,dc]=m.useState([]),[$o,ro]=m.useState(Bf),Sn=Zn($o.status),[uc,yr]=m.useState(null),[fc,Xs]=m.useState(!1),[mc,Qs]=m.useState(null),[pc,Ys]=m.useState(!1),Zs=m.useRef(0),{lastWorkSlot:Ge,rememberLastWorkSlot:Ae}=Hf(i,c?.id??null),[Me,qo]=m.useState(null),[xn,gc]=m.useState(()=>new Set),[Ye,En]=m.useState(null),[An,ea]=m.useState(()=>new Set),[Ir,Cr]=m.useState(()=>new Set),[Sr,ta]=m.useState(()=>new Set),[xr,oa]=m.useState({}),[na,kc]=m.useState({}),[so,ra]=m.useState({}),[z,ke]=m.useState(null),fe=Kf(),[he,Te]=m.useState(null),[Y,No]=m.useState(null),sa=m.useRef(new Map),[ve,Ue]=m.useState(null),[it,Er]=m.useState(null),[bc,Ar]=m.useState(null),[aa,_r]=m.useState(!1),[Lo,Gt]=m.useState(null),[ia,Fo]=m.useState(!1),[wc,hc]=m.useState(null),{scrollRef:Ut,surface:At,zoom:je,revealCell:ao}=Jf(i,c?.id,b==="notebook"),[la,vc]=m.useState(58),[ca,yc]=m.useState(58),Ic=m.useMemo(()=>({"--notebook-command-row-height":`${la}px`,"--notebook-composer-height":`${ca}px`}),[la,ca]),[Rr,me]=m.useState(!1),[Wt,Le]=m.useState(null),[zt,kt]=m.useState(null),[io,_n]=m.useState(null),[Cc,Pr]=m.useState(!1),[Sc,Mr]=m.useState(!1),[xc,Tr]=m.useState(null),[Ec,da]=m.useState(!1),[ue,le]=m.useState(null),[E,O]=m.useState(null),jr=m.useRef(null),ua=m.useRef(null),$r=m.useRef(!1),[qr,lo]=m.useState(""),[G,T]=m.useState(!1),{turns:fa,begin:ma,observe:Rn,cancelReview:pa,claimVoice:ga}=Xf(i,c?.id??null),ka=m.useRef(void 0),[Ac,_c]=m.useState(null),[Rc,Nr]=m.useState(Qf),[Pc,ba]=m.useState(null),[_t,Mc]=m.useState(()=>window.navigator.onLine),[Bt,Do]=m.useState({text:"Connect to the server, then load your books.",tone:"info"}),h=m.useCallback((e,t="info")=>{Do({text:e,tone:t})},[]),Oo=m.useRef(null),Vo=m.useRef(0),_e=m.useRef(0),We=m.useRef(0),Lr=m.useRef(0),Fr=m.useRef(null),Ze=m.useRef(new Map),Go=m.useRef(new Map),Dr=m.useRef(0),Pn=m.useRef(new Map),lt=m.useRef(new Set),Q=m.useRef({bookId:i,notebookId:c?.id??null,assets:B}),Pe=m.useRef(async()=>{throw new Error("MCP call is not ready")}),ye=m.useRef(0),Or=m.useRef(Ve),wa=m.useRef(b),ne=m.useCallback((e,t)=>{ra(o=>{if(t===null){if(!(e in o))return o;const n={...o};return delete n[e],n}return o[e]===t?o:{...o,[e]:t}})},[]);m.useEffect(()=>{if(!Bt||Bt.tone!=="info")return;const e=Bt,t=window.setTimeout(()=>{Do(o=>o===e?null:o)},6e3);return()=>window.clearTimeout(t)},[Bt]);const co=m.useMemo(()=>x.find(e=>e.bookId===i)??null,[i,x]),re=m.useMemo(()=>new Map(B.map(e=>[e.artifactId,e])),[B]),se=m.useMemo(()=>Yf(c?.cells??[],B),[B,c]),Vr=m.useMemo(()=>Zf(c?.cells??[],B),[B,c]),Uo=m.useMemo(()=>[...Vr.values()].flatMap(e=>e.asset?[{...e.asset,cellAddress:e.token.slice(1)}]:[]),[Vr]),U=E?.kind==="generation"?E.draft:null,ha=m.useMemo(()=>{if(E?.kind!=="routed")return null;const e=E.plan;if(e.routedTool!=="change_video_speed")return null;const t=_(e.params.asset_id),o=t?se.find(p=>p.artifactId===t):void 0,n=t?re.get(t):void 0,r=ie(n?.duration)??ie(o?.duration),s=ie(e.params.speed),a=ie(e.params.target_duration_seconds),l=s??(r&&a&&a>0?r/a:null),u=n?.mediaUrl??null,d=n?.type??o?.type??null;return{mediaUrl:u,thumbnailUrl:n?.thumbnailUrl??null,unavailableReason:d!==null&&d!=="video"?"the selected source is not a video":u===null?"the source media is not loaded yet":null,sourceDurationSeconds:r&&r>0?r:null,effectiveSpeed:l&&l>0?l:null}},[re,se,E]),Tc=E?.kind==="routed"?em({input:E.plan.prompt,params:E.plan.params,tool:E.plan.routedTool,sourceDurationSeconds:ha?.sourceDurationSeconds??null}):null,uo=m.useMemo(()=>{if(E?.kind!=="routed")return null;const e=E.plan;if(e.tool!=="post"&&e.routedTool!=="post")return null;const t=_(e.params.asset_id)?.trim()??"",o=t.replace(/^@/,""),n=se.find(u=>u.artifactId===o||u.cellAddress.toLowerCase()===o.toLowerCase()),r=re.get(n?.artifactId??o)??n??null,s=Fi(e.params),a=E.xPostReview,l=a?.options.enabled&&eo(a).length===0?{blocking:Di,notice:null}:tm(s,void 0,Sn);return{asset:r,draft:s,error:Oi(s,void 0,Sn),validation:l,sourceLabel:n?`@${n.cellAddress}`:t.startsWith("@")?t:o?`@${o}`:"Selected media"}},[re,se,E,Sn]),bt=m.useMemo(()=>U&&c?om(U,c):[],[c,U]),Wo=m.useMemo(()=>U?nm(Qe,U.cell.type,bt):[],[Qe,bt,U]),jc=m.useMemo(()=>U?rm(U.action,bt):[],[bt,U]),zo=m.useMemo(()=>U&&c?U.sourceCellIds.flatMap(e=>{const t=c.cells.find(o=>o.id===e);return t?[{cellId:e,address:Se(t.slot),type:t.type,asset:t.outputArtifactId?re.get(t.outputArtifactId)??null:null}]:[]}):[],[re,c,U]),Bo=m.useMemo(()=>{if(!E)return Cs;if(E.kind==="generation"&&U)return{target:Se(U.cell.slot),sources:zo.map(e=>e.address)};if(E.kind==="frame"||E.kind==="split")return{target:null,sources:E.expectations.map(e=>e.address)};if(E.kind==="notebook"){const[e,...t]=E.plan.expectations.map(o=>o.address);return{target:e??null,sources:t}}if(E.kind==="transcribe"&&E.assetId){const e=E.assetId,t=se.find(o=>o.artifactId===e)?.cellAddress;return t?{target:null,sources:[t]}:Cs}return Cs},[se,E,U,zo]),Gr=m.useMemo(()=>sm(Bo),[Bo]),$c=m.useMemo(()=>U&&c?am(c,U.sourceCellIds,U.cell.id).map(({cell:e})=>({cellId:e.id,address:Se(e.slot),type:e.type,asset:e.outputArtifactId?re.get(e.outputArtifactId)??null:null})):[],[re,c,U]),Ur=m.useMemo(()=>im(c?.generationPlans),[c]),w=m.useCallback(async(e,t,o)=>{if(g.state!=="ready")throw new Error("MCP server is not ready");if(o?.chat&&!o.chat.isInScope())throw new Error("Workspace changed. Repeat the command in the current workspace.");if(o?.background||!lm(e)){const l=Vi(await g.callTool(e,t));return o?.chat?.accept(e,t,l),l}const n=Fp(),r=performance.now();Go.current.set(n,{tool:e,startedAt:r}),Nr(l=>cm(l,{id:n,turnId:o?.chat?.visible===!1?void 0:o?.chat?.id,tool:e,args:dm(t)}));let s="done",a="";try{const l=Vi(await g.callTool(e,t));return a=um(l),o?.chat?.accept(e,t,l),l}catch(l){throw s="failed",a=l instanceof Error?l.message:String(l),l}finally{Go.current.delete(n);const l=performance.now()-r,u=()=>{Pn.current.delete(n),Nr(p=>Op(p,n,{phase:s,elapsedMs:l,detail:a})),!(Go.current.size>0)&&(window.clearTimeout(Dr.current),ba(s==="failed"?"error":"success"),Dr.current=window.setTimeout(()=>ba(null),s==="failed"?1100:620))},d=Math.max(0,Dp-l);d===0?u():Pn.current.set(n,window.setTimeout(u,d))}},[g]),Mn=E?.kind==="post-delivery"?E.review:null;fm(!!(Mn?.receipt&&Mn.destination==="icloud"),g.state==="ready"?w:void 0,Mn?.bookId??"",Mn?.postId??"",e=>O(t=>t?.kind==="post-delivery"?{...t,review:{...t.review,sync:e}}:t));const Ho=m.useMemo(()=>i&&c?{bookId:i,notebookId:c.id}:null,[i,c]),{goals:Wr,events:qc,accept:Nc,refresh:va,act:ya}=mm(w,Ho),zr=m.useMemo(()=>new Set((c?.cells??[]).filter(e=>e.type==="goal").map(e=>e.id)),[c]),Ko=m.useMemo(()=>Wr.filter(e=>zr.has(e.cellId)),[zr,Wr]),Ia=m.useMemo(()=>new Map(Ko.map(e=>[e.cellId,e])),[Ko]),Lc=m.useMemo(()=>pm(Ko),[Ko]),fo=gm(Ko),Jo=km({callTool:w,ready:g.state==="ready"}),Br=bm({bookId:i,ready:g.state==="ready",call:w}),Fc=m.useCallback(async e=>{try{const t=D(await w("estimate_cost",{calls:[{tool_name:"edit_image_subjects",input:{model:e}}]})),o=D(t?.estimate),n=Array.isArray(o?.warnings)?o.warnings.filter(l=>typeof l=="string"):[],r=typeof o?.usd=="number"?o.usd:null,s=Gi(n);if(r===null||r<=0||n.length>0&&!s)return null;const a=`$${r.toFixed(r<.01?4:2)}`;return s?`${a} · historical average`:a}catch{return null}},[w]),[Xo,Tn]=m.useState(null),et=wm({bookId:i,ready:g.state==="ready"&&!G,sequence:J,call:w,parseSequence:Ke,parseAssets:Lt,onSequence:e=>{ye.current=performance.now(),Ee(e)},onAssets:e=>Je(t=>{const o=new Map(t.map(n=>[n.artifactId,n]));for(const n of e)o.set(n.artifactId,n);return[...o.values()]})}),wt=hm({bookId:i,ready:g.state==="ready",sequence:J,call:w,onSequence:e=>{const t=Ke(e);t&&(ye.current=performance.now(),Ee(t))}}),jn=Xo?.bookId===i?c?.cells.find(e=>e.id===Xo.cellId&&e.type==="timeline"):void 0,Qo=!!(jn&&J&&b==="notebook"),{preview:Ca,select:Yo}=vm({bookId:i,notebook:c,ready:g.state==="ready",call:w}),Dc=m.useCallback(e=>{Nr(t=>ym(t,e))},[]);m.useEffect(()=>()=>{window.clearTimeout(Dr.current);for(const e of Pn.current.values())window.clearTimeout(e);Pn.current.clear()},[]),m.useEffect(()=>{Pe.current=w},[w]),m.useEffect(()=>{Q.current={bookId:i,notebookId:c?.id??null,assets:B}},[B,i,c?.id]),m.useEffect(()=>{Or.current=Ve},[Ve]),m.useEffect(()=>{wa.current=b},[b]);const ct=m.useCallback(e=>{Rn(Q.current.bookId??"",e);const t=!Nt(Or.current,e);t&&(Or.current=e,Ws(e));const o=wa.current==="jobs"&&e.some(n=>tw.has(n.state));(t||o)&&zs(Date.now())},[Rn]),Rt=m.useCallback((e,t,o=null)=>{oa(n=>({...n,[e]:{operation:t,error:o}}))},[]),Zo=m.useCallback((e,t)=>{Rt(e,null,t)},[Rt]),oe=m.useCallback((e,t)=>{ea(o=>{const n=new Set(o);return t?n.add(e):n.delete(e),n.size===o.size?o:n})},[]),en=m.useCallback(e=>{Cr(t=>new Set([...t,...e])),window.setTimeout(()=>{Cr(t=>{const o=new Set(t);for(const n of e)o.delete(n);return o.size===t.size?t:o})},900)},[]),[Hr,Sa]=m.useState(()=>new Set),mo=m.useRef(null);m.useEffect(()=>()=>{mo.current!==null&&window.clearTimeout(mo.current)},[]);const po=m.useCallback((e,t={})=>{Sa(o=>Im(o,e)),mo.current!==null&&window.clearTimeout(mo.current),mo.current=window.setTimeout(()=>{mo.current=null,Sa(o=>Cm(o,e))},Sm),t.scroll&&window.requestAnimationFrame(()=>{if(t.scroll==="offscreen"&&Oo.current?.getNodes().some(n=>n.dragging))return;const o=window.matchMedia("(prefers-reduced-motion: reduce)").matches;for(const n of e){const r=document.querySelector(`[data-id="${n}"]`);if(r){if(t.scroll==="offscreen"){const s=r.getBoundingClientRect();if(s.top>=0&&s.left>=0&&s.bottom<=window.innerHeight&&s.right<=window.innerWidth)continue}r.scrollIntoView({block:"center",behavior:o?"auto":"smooth"})}}})},[]),go=m.useCallback(()=>{Ui(()=>document.querySelector('.command-composer [aria-label="Videobook command input"]'))},[]);m.useEffect(()=>{const e=()=>Mc(window.navigator.onLine);return window.addEventListener("online",e),window.addEventListener("offline",e),()=>{window.removeEventListener("online",e),window.removeEventListener("offline",e)}},[]);const ko=m.useCallback(async(e,t,o)=>{if(!i||!c)throw new Error("Load a notebook first.");return ft(await w("plan_notebook_generation",{book_id:i,notebook_id:c.id,cell_id:e,source_surface:t,actor:"videobook-user",timeline_start_frame:0},{chat:o}))},[i,w,c]),Kr=m.useCallback(async(e,t,o)=>{const n=await ko(e,t,o);return L(o,!1,()=>O(null)),L(o,!0,()=>le({plan:n,previews:{}})),M(o,()=>go()),pt("Generation plan ready for review")},[ko,go]),[ze,ht]=m.useState(()=>k?.notebook?Ss(k.notebook,k.assets,k.jobs):[]),[xa,$n]=m.useState(()=>k?.notebook?Wi(k.notebook):[]),bo=m.useCallback(e=>{e.size>0&&ke(o=>o?.cellId===null?null:o);const t=lt.current;t.size===e.size&&[...e].every(o=>t.has(o))||(lt.current=e,gc(e))},[]),Z=m.useCallback((e,t,o)=>{if(t&&!t.isCurrent()||(_c(e?t?.id??null:null),qo(e),Yo(e,o),bo(e?new Set([e]):new Set),!e))return;const n=c?.cells.find(s=>s.id===e);if(n){Ae(n.slot);return}const r=ze.find(s=>s.id===e);r&&Ae(r.data.slot)},[Yo,c,ze,Ae,bo]),wo=m.useCallback(()=>{En(null)},[]),Ea=m.useCallback((e,t,o)=>{Z(e),En({target:{kind:"cell",cellId:e},position:t,returnFocus:o})},[Z]),Oc=m.useCallback((e,t,o)=>{En({target:{kind:"slot",slot:e},position:t,returnFocus:o})},[]),Ht=Ye?.target.kind==="cell"?Ye.target.cellId:null,Vc=m.useMemo(()=>({openCellId:Ht,open:Ea}),[Ht,Ea]),Ie=m.useCallback((e,t,o,n=i)=>{Rn(n,o,e,t),ye.current=performance.now(),xe(s=>Nt(s,e)?s:e);const r=new Set(e.cells.map(s=>s.id));ea(s=>{const a=new Set([...s].filter(l=>r.has(l)));return a.size===s.size?s:a}),Cr(s=>{const a=new Set([...s].filter(l=>r.has(l)));return a.size===s.size?s:a}),oa(s=>Object.keys(s).every(a=>r.has(a))?s:Object.fromEntries(Object.entries(s).filter(([a])=>r.has(a)))),ra(s=>Object.keys(s).every(a=>r.has(a))?s:Object.fromEntries(Object.entries(s).filter(([a])=>r.has(a)))),bo(new Set([...lt.current].filter(s=>r.has(s)))),ke(s=>s&&s.bookId===n&&s.notebookId===e.id&&(s.cellId===null||r.has(s.cellId))?s:null),En(s=>!s||s.target.kind==="slot"||r.has(s.target.cellId)?s:null),ht(s=>xm(s,Ss(e,t,o))),$n(s=>Em(s,Wi(e))),qo(s=>s&&e.cells.some(a=>a.id===s)?s:null),Le(s=>s&&r.has(s)?s:null)},[i,Rn,bo]);Am({bookId:i,notebookId:c?.id??null,enabled:g.state==="ready"&&b==="notebook"&&!G&&!et.busy&&!ze.some(e=>e.dragging),refresh:async e=>{if(g.state!=="ready"||!c||Go.current.size>0)return;const t=performance.now(),o=zr.size>0||Wr.length>0,[n,r,s,a,l]=await Promise.allSettled([w("get_notebook",{book_id:i,notebook_id:c.id},{background:!0}),w("list_assets",{book_id:i,sort:"newest",limit:200,include_referenced:!0},{background:!0}),w("list_jobs",{book_id:i,limit:200},{background:!0}),c.cells.some(v=>v.type==="timeline")?w("get_primary_sequence",{book_id:i},{background:!0}):Promise.resolve(null),o?w("video_goal",{book_id:i,notebook_id:c.id,action:"list"},{background:!0}):Promise.resolve(null)]);if(!e()||Go.current.size>0||(l.status==="fulfilled"&&l.value&&Nc({bookId:i,notebookId:c.id},l.value),t<ye.current)||n.status!=="fulfilled"||r.status!=="fulfilled"||s.status!=="fulfilled")return;const u=ge(n.value);if(!u)return;const d=Lt(r.value),p=to(s.value);if(Je(v=>Nt(v,d)?v:d),a.status==="fulfilled"&&a.value){const v=Ke(a.value);v&&Ee(S=>Nt(S,v)?S:v)}ct(p),Ie(u,d,p)}});const Pt=m.useCallback(async e=>{Ze.current.set(e.cellId,e.runId);let t=!1,o=0;const n=Date.now()+e.timeoutMs,r=()=>{const l=Q.current;return l.bookId===e.bookId&&l.notebookId===e.notebookId},s=async()=>{const l=performance.now(),[u,d,p]=await Promise.all([Pe.current("get_notebook",{book_id:e.bookId,notebook_id:e.notebookId},{background:!0}),Pe.current("list_assets",{book_id:e.bookId,sort:"newest",limit:200,include_referenced:!0},{background:!0}),Pe.current("list_jobs",{book_id:e.bookId,limit:200},{background:!0})]);if(!r())return;const v=ge(u);if(!v)return;const S=Lt(d),A=to(p);l<ye.current||(ye.current=l,Je(y=>Nt(y,S)?y:S),ct(A),Ie(v,S,A))},a=async()=>{for(let l=0;l<Kb;l+=1){if(!r())return;try{await s();return}catch{await rt(Jb)}}};try{for(;Date.now()<n;){if(Ze.current.get(e.cellId)!==e.runId)return{kind:"superseded"};const l=Q.current;if(l.bookId!==e.bookId||l.notebookId!==e.notebookId)return{kind:"superseded"};try{const u=performance.now(),[d,p]=await Promise.all([Pe.current("get_notebook",{book_id:e.bookId,notebook_id:e.notebookId},{background:!0}),Pe.current("list_jobs",{book_id:e.bookId,limit:200},{background:!0})]);o=0;const v=Q.current;if(v.bookId!==e.bookId||v.notebookId!==e.notebookId||Ze.current.get(e.cellId)!==e.runId)return{kind:"superseded"};const S=ge(d);if(!S)throw new Error("The server returned an invalid notebook");const A=to(p),y=u>=ye.current;y&&(ye.current=u,ct(A));const R=A.map(zi),q=_m({jobs:R,cellId:e.cellId,runId:e.runId,jobOperationId:e.jobOperationId}),V=Rm(S,e.cellId,e.runId);V.state!=="pending"&&oe(e.cellId,!1),y&&Ie(S,v.assets,A);const X=Pm({observation:V,job:q,address:e.address,sawRun:t});if(X.kind==="continue"){t=X.sawRun,await rt(e.intervalMs);continue}return X.kind==="completed"?(await a(),ne(e.cellId,null),{kind:"completed"}):X.kind==="failed"?{kind:"failed",message:X.message}:{kind:"superseded"}}catch(u){if(o+=1,o>=e.maxPollFailures){const d=u instanceof Error?u.message:String(u);return await a(),{kind:"failed",message:`Lost contact with the server while watching @${e.address}: ${d}`}}await rt(e.intervalMs)}}return await a(),{kind:"timeout"}}finally{Ze.current.get(e.cellId)===e.runId&&Ze.current.delete(e.cellId)}},[ct,Ie,oe,ne]),tn=m.useCallback(async(e,t)=>{try{const o=await Pt({...e,intervalMs:Xb,timeoutMs:Qb,maxPollFailures:10});if(o.kind==="completed"){M(t,()=>{h(`@${e.address} generated`),po([e.cellId],{scroll:"offscreen"})}),ne(e.cellId,null);return}if(o.kind==="failed"){const n=o.message??`@${e.address} failed`;ne(e.cellId,n),M(t,()=>h(n,"error"));return}o.kind==="timeout"&&M(t,()=>h(`@${e.address} is still running — check the Jobs screen`))}catch(o){const n=o instanceof Error?o.message:String(o);ne(e.cellId,n),M(t,()=>h(n,"error"))}finally{oe(e.cellId,!1)}},[po,oe,ne,h,Pt]),qn=m.useCallback(async e=>{const t=e.intervalMs??Gl,o=`${e.tokenPrefix??"media"}:${e.artifactId}`;Ze.current.set(e.cellId,o);let n=e.artifactId,r=0;const s=Date.now()+Wl;try{for(;Date.now()<s;){const a=Q.current;if(Ze.current.get(e.cellId)!==o||a.bookId!==e.bookId||a.notebookId!==e.notebookId)return;try{const l=performance.now(),[u,d,p]=await Promise.all([Pe.current("get_notebook",{book_id:e.bookId,notebook_id:e.notebookId},{background:!0}),Pe.current("list_assets",{book_id:e.bookId,sort:"newest",limit:200,include_referenced:!0},{background:!0}),Pe.current("list_jobs",{book_id:e.bookId,limit:200},{background:!0})]);r=0;const v=Q.current;if(Ze.current.get(e.cellId)!==o||v.bookId!==e.bookId||v.notebookId!==e.notebookId)return;const S=ge(u);if(!S)throw new Error("The server returned an invalid notebook");const A=S.cells.find(V=>V.id===e.cellId);if(!A||A.outputArtifactId!==n)return;const y=Lt(d),R=to(p);l>=ye.current&&(ye.current=l,Je(V=>Nt(V,y)?V:y),ct(R),Ie(S,y,R));const q=Mm(n,y.find(V=>V.artifactId===n),R,Tm(S,e.cellId));if(q.kind==="redirected"){const V=y.find(P=>P.artifactId===q.artifactId),X=V?Os(V.type):null;if(!V||!X){await rt(t);continue}await Pe.current("update_notebook_cell",{book_id:e.bookId,notebook_id:e.notebookId,cell_id:e.cellId,cell:{type:X,output_artifact_id:V.artifactId}},{background:!0}),n=V.artifactId,ne(e.cellId,null);continue}if(q.kind==="completed"){ne(e.cellId,null),e.completedNotice&&h(e.completedNotice);return}if(q.kind==="failed"){ne(e.cellId,q.message),h(q.message,"error");return}await rt(t)}catch(l){if(r+=1,r>=10){const u=l instanceof Error?l.message:String(l);h(`Stopped watching @${e.address}: ${u}. Check the Jobs screen.`,"error");return}await rt(t)}}h(e.stillWorkingNotice??`@${e.address} is still processing — check the Jobs screen`)}finally{Ze.current.get(e.cellId)===o&&Ze.current.delete(e.cellId)}},[ct,Ie,ne,h]),Gc=m.useCallback(async e=>{await qn({...e,tokenPrefix:"download",intervalMs:Gl,completedNotice:`@${e.address} downloaded`,stillWorkingNotice:`@${e.address} is still downloading — check the Jobs screen`})},[qn]),Nn=m.useCallback(async e=>{await qn({...e,tokenPrefix:"process",intervalMs:Ul,stillWorkingNotice:`@${e.address} is still processing — check the Jobs screen`})},[qn]),Ln=m.useCallback((e,t,o)=>{const n=new Map(o.map(r=>[r.artifactId,r]));for(const r of t.cells){if(!Ft(r.type)||!r.outputArtifactId)continue;const s=n.get(r.outputArtifactId);!s||s.status==="ready"||s.status==="error"||Ze.current.has(r.id)||Nn({bookId:e,notebookId:t.id,cellId:r.id,address:Se(r.slot),artifactId:r.outputArtifactId})}},[Nn]),Aa=m.useRef(!1);m.useEffect(()=>{Aa.current||!i||!c||(Aa.current=!0,Ln(i,c,B))},[B,i,c,Ln]);const ae=m.useCallback(e=>{const t=Q.current;t.bookId!==i||t.notebookId!==c?.id||$r.current||M(e,()=>me(!1))},[i,c?.id]),on=m.useCallback(async(e,t,o,n)=>{if(!i||!c)return;let r=!1;T(!0),ne(e,null);try{const s=t??ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(!s)throw new Error("The server returned an invalid notebook");const a=s.cells.find(S=>S.id===e);if(!a||!rw(a))throw new Error("Configure this cell before running it");const l=jm(a);if(l&&!_t)throw new Error("Offline: cloud generation is unavailable. Local search, editing, playback, and export remain available.");if(l){if(Bi(a)){const A=await ko(e,"ui",o),y=A.stages.find(de=>de.kind==="queued"&&de.jobType==="generation"&&de.tool==="run_notebook_cell"&&de.input.cell_id===e);if(y?.kind!=="queued")throw new Error("The generation plan is missing its notebook cell");const R=_(y.input.notebook_id);if(R!==s.id)throw new Error("The generation plan belongs to another notebook");if(!ur(y))throw new Error("Cloud generation cancelled before sending data");L(o,!1,()=>O(null)),L(o,!1,()=>le(null));const q=await er({start:()=>w("run_notebook_cell",{book_id:i,notebook_id:R,cell_id:e,plan:A,...n?{retry_failed_cell_id:n}:{},actor:"videobook-user"},{chat:o}),onStarting:()=>oe(e,!0),onAccepted:()=>oe(e,!1),onRejected:()=>oe(e,!1)}),V=D(q),X=_(V?.run_id),P=_(V?.job_id),N=_(V?.output_cell_id);if(!X||!P)throw oe(e,!1),new Error("The server did not return a notebook run");r=!0,N&&ae(o);const H=N??e;let te=Se(a.slot);if(N){const de=await w("get_notebook",{book_id:i,notebook_id:R},{background:!0,chat:o}),pe=ge(de);if(pe){Ie(pe,B,Ve);const He=pe.cells.find(be=>be.id===N);He&&(te=Se(He.slot))}M(o,()=>en([N])),ne(N,null),oe(N,!0),lt.current.has(e)&&(Z(null,o),M(o,()=>po([N],{scroll:"center"})))}return M(o,()=>h(`${W(a.slot)} queued`)),tn({bookId:i,notebookId:R,cellId:H,address:te,runId:X,jobOperationId:P},o),{ok:!0,message:`${W(a.slot)} queued`}}const S=await Kr(e,"ui",o);return M(o,()=>h(S.message,S.ok?"info":"error")),S}const u=await er({start:()=>w("run_notebook_cell",{book_id:i,notebook_id:s.id,cell_id:e,actor:"videobook-user",...s.revision?{expected_revision:s.revision}:{}},{chat:o}),onStarting:()=>oe(e,!0),onRejected:()=>oe(e,!1)}),d=_(D(u)?.run_id),p=_(D(u)?.job_id);if(!d||!p)throw new Error("The server did not return a notebook run");M(o,()=>h(`${W(a.slot)} queued`));const v=await Pt({bookId:i,notebookId:s.id,cellId:e,address:Se(a.slot),runId:d,jobOperationId:p,intervalMs:wn,timeoutMs:hn,maxPollFailures:fr});if(v.kind==="failed")throw new Error(v.message??`${W(a.slot)} failed`);if(v.kind==="timeout")throw new Error("Notebook run did not finish within five minutes");return v.kind==="completed"&&M(o,()=>h(`${W(a.slot)} updated`)),{ok:!0,message:`${W(a.slot)} run accepted`}}catch(s){const a=s instanceof Error?s.message:String(s);return ne(e,a),M(o,()=>h(a,"error")),{ok:!1,message:a}}finally{r||oe(e,!1),T(!1)}},[Ie,B,i,w,ae,ko,po,Ve,c,_t,Kr,en,Z,oe,ne,h,tn,Pt]),Mt=m.useMemo(()=>{let e=ze;for(const t of An)e=$m(e,t,"queued");return Ir.size>0&&(e=e.map(t=>Ir.has(t.id)?{...t,data:{...t.data,revealing:!0}}:t)),Hr.size>0&&(e=e.map(t=>Hr.has(t.id)?{...t,data:{...t.data,highlighted:!0}}:t)),Object.keys(so).length===0?e:e.map(t=>{const o=so[t.id];return o?{...t,data:{...t.data,status:"error",statusError:o}}:t})},[so,Hr,ze,An,Ir]),Uc=m.useMemo(()=>Mt.map(e=>{const t=xn.has(e.id),o=Gr.get(Se(e.data.slot)),n=o?`notebook-review-${o}`:void 0;return e.selected===t&&e.className===n?e:{...e,selected:t,className:n}}),[Gr,Mt,xn]),Wc=m.useMemo(()=>qm(xa,Me),[xa,Me]),vt=m.useMemo(()=>ze.flatMap(e=>Tl({type:e.data.kind,slot:e.data.slot})),[ze]),_a=m.useMemo(()=>ze.map(e=>({type:e.data.kind,slot:e.data.slot})),[ze]),Jr=m.useMemo(()=>Hi(vt,{viewportWidth:At.width,viewportHeight:At.height,zoom:je}),[vt,At.height,At.width,je]),Tt=m.useMemo(()=>Lo?Hi(vt,{preview:Lo,viewportWidth:At.width,viewportHeight:At.height,zoom:je}):Jr,[vt,Jr,At.height,At.width,je,Lo]),Fn=m.useMemo(()=>Nm(Tt,je),[Tt,je]),zc=m.useMemo(()=>Lm(Fm(_a,Tt.rowCount)),[_a,Tt.rowCount]),Bc=m.useMemo(()=>({"--notebook-detail-scale":Ki(je),width:Fn.width,height:Fn.height}),[Fn.height,Fn.width,je]),Hc=m.useMemo(()=>Dm(Tt,je),[Tt,je]),Kc=m.useCallback(()=>{b==="notebook"&&Om(()=>Ut.current)},[Ut,b]),Fe=m.useCallback(()=>{if(pa(),jr.current?.({status:"cancelled",message:"Pending action cancelled on screen."}),E?.kind==="chain-step"&&i){const e=E.chainId;Ot("videobook.active-chain",""),w("chain",{action:"cancel",book_id:i,chain_id:e}).catch(()=>{})}le(null),O(null),Te(null),go()},[i,w,pa,go,E]),Jc=m.useCallback(e=>{O(t=>t?.kind!=="routed"||t.plan.tool!=="post"&&t.plan.routedTool!=="post"?t:{...t,plan:{...t.plan,params:Vm(t.plan.params,e)}})},[]),Xc=m.useCallback(e=>{O(t=>{if(t?.kind!=="routed"||!t.xPostReview)return t;const o={...t.xPostReview,options:{...t.xPostReview.options,...e}};return{...t,xPostReview:o,plan:{...t.plan,params:pn(t.plan.params,eo(o))}}})},[]),Ra=m.useCallback(e=>{O(t=>{if(t?.kind!=="routed"||!t.xPostReview)return t;const o=Gm(t.xPostReview,e);return o===t.xPostReview?t:{...t,xPostReview:o,plan:{...t.plan,params:pn(t.plan.params,eo(o))}}})},[]),Qc=m.useCallback((e,t)=>{O(o=>{if(o?.kind!=="routed"||!o.xPostReview)return o;const n={...o.xPostReview,promptOverrides:{...o.xPostReview.promptOverrides,[e]:t}};return{...o,xPostReview:n,plan:{...o.plan,params:pn(o.plan.params,eo(n))}}})},[]),Yc=m.useCallback(e=>{O(t=>{if(t?.kind!=="routed"||!t.xPostReview)return t;const o={...t.xPostReview,creditsOverride:e};return{...t,xPostReview:o,plan:{...t.plan,params:pn(t.plan.params,eo(o))}}})},[]),Zc=m.useCallback(e=>{O(t=>{if(t?.kind!=="split")return t;const o=t.expectations[0]?.address??"video",n={...t.command,cutPointsSeconds:e.cutPointsSeconds,outputMode:e.outputMode,selectedChunkIndexes:[e.selectedIndex]};return{...t,command:n,summary:Ji({cutPointsSeconds:n.cutPointsSeconds,outputMode:n.outputMode,selectedChunkIndexes:n.selectedChunkIndexes,sourceAddress:o,sourceDurationSeconds:t.sourceDurationSeconds})}})},[]),Xr=m.useCallback(async(e,t,o)=>{if(!i)throw new Error("Open a book before previewing generation.");return await w("preview_notebook_generation",{book_id:i,notebook_id:t.id,cell_id:e.cell.id,draft:{type:e.cell.type,...e.cell.label===void 0?{}:{label:e.cell.label},slot:e.cell.slot,prompt:Um(e,t),provider:e.cell.provider??e.action.provider,model:e.cell.model??e.action.model,operation:e.cell.operation??e.action.operation,tool:e.cell.tool??e.action.tool,inputs:e.cell.inputs??{}},connections:e.connections.map(n=>({source_cell_id:n.sourceCellId,target_input:n.targetInput}))},{chat:o,background:!0})},[i,w]),ho=m.useRef(0);m.useEffect(()=>()=>{ho.current+=1},[i,c?.id]);const jt=m.useCallback((e,t,o)=>{const n=++ho.current,r=JSON.stringify({id:e.cell.id,prompt:e.cell.prompt,action:e.action.id,inputs:e.cell.inputs,connections:e.connections});M(o,()=>O(s=>s?.kind==="generation"&&s.draft.cell.id===e.cell.id?{...s,previewError:null,previewLoading:!0,previewStale:!0}:s)),Xr(e,t,o).then(s=>{ho.current===n&&M(o,()=>O(a=>a?.kind!=="generation"?a:JSON.stringify({id:a.draft.cell.id,prompt:a.draft.cell.prompt,action:a.draft.action.id,inputs:a.draft.cell.inputs,connections:a.draft.connections})===r?{...a,preview:s,previewError:null,previewLoading:!1,previewStale:!1}:a))}).catch(s=>{ho.current===n&&M(o,()=>O(a=>a?.kind!=="generation"?a:JSON.stringify({id:a.draft.cell.id,prompt:a.draft.cell.prompt,action:a.draft.action.id,inputs:a.draft.cell.inputs,connections:a.draft.connections})===r?{...a,previewError:s instanceof Error?s.message:String(s),previewLoading:!1,previewStale:!1}:a))})},[Xr]),$t=Wm(jt,`${i}:${c?.id}:${U?.cell.id}`),yt=m.useCallback((e,t)=>{ho.current+=1,$t.cancel(),O(o=>o?.kind==="generation"&&o.draft.cell.id===e.cell.id?{...o,draft:e,previewError:null,previewLoading:!1,previewStale:!0}:o),c&&(t?jt(e,c):$t.schedule(e,c))},[c,$t,jt]),Pa=m.useCallback(e=>{U&&yt(tr(U,e),!1)},[U,yt]),ed=zm({call:g.state==="ready"?w:void 0,bookId:i??"",surface:U?Bm(U.cell.type):null,prompt:U?.cell.prompt??"",onApply:Pa}),td=m.useCallback(e=>{if(!U)return;const t=Wo.find(o=>o.id===e);t&&yt(Xi(U,t,bt),!0)},[Wo,bt,U,yt]),od=m.useCallback(e=>{U&&yt(Hm(U,e,bt),!0)},[bt,U,yt]),nd=m.useCallback((e,t)=>{U&&yt(xs(U,e,t),!0)},[U,yt]),rd=m.useCallback(()=>{!U||!c||($t.cancel(),jt(U,c))},[c,U,$t,jt]),sd=m.useCallback(e=>{Z(e),no("selection")&&me(!0)},[Z]),Dn=m.useCallback(e=>{if(!U||!c)return;let t;try{t=Km({actions:Qe,draft:U,document:c,sourceCellIds:e})}catch(r){h(r instanceof Error?r.message:String(r),"error");return}const o=[...t.sourceCellIds.flatMap(r=>{const s=c.cells.find(a=>a.id===r);return s?[{address:W(s.slot),cellId:s.id}]:[]}),{address:W(t.cell.slot),cellId:null}],n=t.sourceAddresses.length>0?` from ${t.sourceAddresses.join(", ")}`:"";O(r=>r?.kind==="generation"&&r.draft.cell.id===t.cell.id?{...r,draft:t,expectations:o,previewError:null,previewLoading:!1,previewStale:!0,summary:`Generate ${Gs(t.cell.type)} as ${W(t.cell.slot)}${n}`}:r),$t.cancel(),jt(t,c)},[Qe,c,U,$t,jt,h]),ad=m.useCallback(e=>{U&&Dn([...U.sourceCellIds,e])},[U,Dn]),id=m.useCallback(e=>{U&&Dn(U.sourceCellIds.filter(t=>t!==e))},[U,Dn]),Qr=m.useMemo(()=>{const e=Bo.target??Bo.sources[0]??null;return e?jl(e)?.row??null:null},[Bo]);m.useEffect(()=>{b!=="notebook"||Qr===null||Jm(()=>Ut.current,{row:Qr,zoom:je},{reducedMotion:typeof window<"u"&&typeof window.matchMedia=="function"&&window.matchMedia("(prefers-reduced-motion: reduce)").matches})},[Ut,je,Qr,b]);const ce=m.useMemo(()=>Mt.find(e=>e.id===Me)??null,[Mt,Me]),$=m.useMemo(()=>c?.cells.find(e=>e.id===Me)??null,[c,Me]),It=m.useMemo(()=>(c?.cells??[]).filter(e=>xn.has(e.id)).sort((e,t)=>e.slot.row-t.slot.row||e.slot.column-t.slot.column),[c,xn]),nn=m.useMemo(()=>new Map((c?.cells??[]).flatMap(e=>{const t=Xm(re,e.outputArtifactId);return t?[[e.id,t]]:[]})),[re,c]),ld=m.useMemo(()=>new Set([...nn].flatMap(([e,t])=>t.type==="video"||t.type==="final"?[e]:[])),[nn]),Ma=m.useMemo(()=>new Set([...nn].flatMap(([e,t])=>t.type==="image"?[e]:[])),[nn]),Ta=c&&$?Qm(c,$.id).error??so[$.id]??null:null,ja=m.useMemo(()=>Ve.map(zi),[Ve]),Yr=$?Ym({cell:$,cells:c?.cells??[],edges:c?.edges??[],queuedCellIds:An,runErrors:so,error:Ta,jobs:ja}):null,cd=m.useMemo(()=>!$||$.type!=="audio"&&$.type!=="image"&&$.type!=="video"&&$.type!=="analysis"?[]:Zm($.inputs,$.outputArtifactId).flatMap(e=>{const t=re.get(e);return t?[t]:[]}),[re,$]),dd=m.useMemo(()=>{if(!c||!$)return null;try{const e=St(c,$.id),t=dr(c,e),o=t?re.get(t):void 0,n=o?.duration??ie(e.inputs?.durationSeconds);return!o?.mediaUrl||!n||n<1?null:{source:e,asset:o,duration:n}}catch{return null}},[re,c,$]),$a=m.useMemo(()=>{if(!c||E?.kind!=="split")return null;try{const e=St(c,E.command.sourceReference),t=dr(c,e),o=t?re.get(t):void 0,n=o?.duration??ie(e.inputs?.durationSeconds);if(!o?.mediaUrl||!n||n<1)return null;const r=gn.maximumRowCount*gn.columnCount;return{availableEmptyCells:Math.max(0,r-c.cells.length),cutPointsSeconds:E.command.cutPointsSeconds,mediaUrl:o.mediaUrl,outputMode:E.command.outputMode??"all",selectedIndex:E.command.selectedChunkIndexes?.[0]??0,sourceDurationSeconds:n,sourceFps:o.fps,sourceLabel:W(e.slot)}}catch{return null}},[re,c,E]),ud=$?xr[$.id]:void 0,fd=m.useCallback(async(e,t)=>{if(!i||!c)throw new Error("Notebook is not ready");return await w("preview_notebook_generation",{book_id:i,notebook_id:c.id,cell_id:e,draft:t},{background:!0})},[i,w,c]),md=m.useCallback(async e=>{if(!i)throw new Error("Book is not ready");const o=await w("inspect_generation_request",{book_id:i,asset_id:e},{background:!0});if(o.payload==null)throw new Error("No generation payload recorded for this attempt");return o.payload},[i,w]),pd=m.useCallback(async e=>{if(!i)throw new Error("Book is not ready");const t=await w("inspect_generation_request",{book_id:i,asset_id:e},{background:!0});return ep(t)},[i,w]),rn=m.useCallback((e,t)=>{kc(o=>({...o,[e]:{...o[e]??Qi,...t}}))},[]),gd=m.useCallback(async e=>{const t=Date.now()+Zb;for(;Date.now()<t;){await rt(Yb);const o=Q.current;if(o.bookId!==e.bookId||o.notebookId!==e.notebookId)return{kind:"continue"};const n=performance.now(),[r,s,a]=await Promise.all([Pe.current("get_notebook",{book_id:e.bookId,notebook_id:e.notebookId},{background:!0}),Pe.current("list_assets",{book_id:e.bookId,sort:"newest",limit:200,include_referenced:!0},{background:!0}),Pe.current("list_jobs",{book_id:e.bookId,limit:200},{background:!0})]),l=ge(r),u=Lt(s),d=to(a);l&&n>=ye.current&&(ye.current=n,Je(S=>Nt(S,u)?S:u),ct(d),Ie(l,u,d));const p=u.find(S=>S.artifactId===e.artifactId),v=tp({insight:e.insight,artifactId:e.artifactId,since:e.since,hasInsight:zl(p,e.insight),hadInsight:e.hadInsight,jobs:d});if(v.kind!=="continue")return v}return{kind:"failed",message:e.insight==="transcript"?"Transcription did not finish in time. Check the jobs screen.":"Video analysis did not finish in time. Check the jobs screen."}},[ct,Ie]),kd=m.useCallback(async(e,t)=>{if(!i)throw new Error("Book is not ready");const o=await w("read_transcript",{book_id:i,asset_id:e,raw:!0,source:t},{background:!0}),n=D(o),r=typeof n?.text=="string"?n.text:null,s=_(n?.file);if(!r||!s)throw new Error("No transcript sidecar for this asset");return{text:r,file:s}},[i,w]),bd=m.useCallback(e=>{i&&w("export_transcript_srt",{book_id:i,asset_id:e}).then(t=>{const o=D(t),n=_(o?.path);h(n?`Saved ${n}`:"Saved SRT to Downloads")}).catch(t=>{h(t instanceof Error?t.message:String(t),"error")})},[i,w,h]),$e=m.useCallback(async(e,t,o)=>{const n=await w("get_notebook",{book_id:e,notebook_id:t},{background:!0,chat:o}),r=ge(n);if(!r)throw new Error("The server returned an invalid notebook");if(o&&!o.isInScope())throw new Error("Workspace changed while refreshing the notebook.");return Ie(r,B,Ve,e),r},[Ie,B,w,Ve]),F=m.useCallback(async(e,t,o,n)=>{if(o?.()===!1||n&&!n.isInScope())return;const r=Lr.current+1;Lr.current=r;const s=await Yi(async()=>await Promise.all([w("list_notebooks",{book_id:e},{background:!0,chat:n}),w("list_assets",{book_id:e,sort:"newest",limit:200,include_referenced:!0},{background:!0,chat:n}),w("get_primary_sequence",{book_id:e},{background:!0,chat:n}),w("list_jobs",{book_id:e,limit:200},{background:!0,chat:n}),w("list_notebook_actions",{book_id:e},{background:!0,chat:n})]),()=>Lr.current===r&&o?.()!==!1&&(!n||n.isInScope()));if(s.kind==="stale")return;if(s.kind==="error")throw s.error;const[a,l,u,d,p]=s.value,v=Zi(a),S=Lt(l),A=to(d),y=yn(`videobook.active-notebook:${e}`),R=v.find(q=>q.id===t)??v.find(q=>q.id===y)??v[0]??null;if(K(e),Ot("videobook.active-book",e),Je(S),Ee(Ke(u)),Ws(A),Js(op(p)),zs(Date.now()),!R){xe(null),ht([]),$n([]);return}return Ot(`videobook.active-notebook:${e}`,R.id),Ie(R,S,A,e),Ln(e,R,S),R.cells.some(q=>q.type==="goal")&&va({bookId:e,notebookId:R.id}).catch(()=>{}),R},[Ie,w,va,Ln]),Zr=e=>{tt("notebook"),Qt(e),ao(e)},wd=async(e="",t)=>{if(!i||!c)return{ok:!1,message:"Open a notebook first."};if(!e)return fo?(Zr(fo.cellId),{ok:!0,message:`Opened goal ${fo.address??""}`.trim()}):{ok:!1,message:"Mention the reference images or videos, for example /goal @a1 @a2 as a short clip."};if(ob(e).length===0)return{ok:!1,message:"Mention the reference images or videos, for example /goal @a1 @a2 as a short clip"};const o={bookId:i,notebookId:c.id},n=await ya(o,{action:"create",brief:e,request_id:xt()},t);return Q.current.bookId!==o.bookId||Q.current.notebookId!==o.notebookId||t?.isCurrent()===!1?{ok:!0,message:"Goal saved in its notebook."}:(await F(o.bookId,o.notebookId,void 0,t),ao(n.cellId),ae(t),Zr(n.cellId),{ok:!0,message:`Planning your video goal in ${n.address??"a new tile"}`})},hd=async e=>{if(!Ho)throw new Error("Open the goal notebook first.");const t=Ho,o=await ya(t,e);return e.action==="combine"?(await F(t.bookId,t.notebookId),o):(e.action!=="approve"&&e.action!=="regenerate"&&e.action!=="revise"&&e.action!=="retry"||(Q.current.bookId===t.bookId&&Q.current.notebookId===t.notebookId&&ae(),await F(t.bookId,t.notebookId)),o)},vd=async e=>{if(!Ho)return;const t=Ho,n=(await F(t.bookId,t.notebookId,()=>Q.current.bookId===t.bookId&&Q.current.notebookId===t.notebookId))?.cells.find(r=>r.type==="timeline");if(!n)throw new Error("Add a timeline cell to preview the assembled sequence.");bs(n.id,e)},dt=m.useCallback((e,t,o=!1)=>{No(n=>n?.key===e?{...n,subjectMap:t,subjectMapLoading:o}:n)},[]),On=m.useCallback(async(e,t,o)=>{const n=await np({initialMap:o,read:async()=>Fs(e,await w("get_image_subject_map",{book_id:e.bookId,artifact_id:e.asset.artifactId,object_hash:e.asset.objectHash},{background:!0})),publish:r=>dt(e.key,r),isCurrent:()=>We.current===t});n.kind==="stale"||n.kind==="terminal"||We.current!==t||dt(e.key,Ds(e,n.kind==="timeout"?new Error("Subject analysis did not finish within 27 minutes. Retry to check or restart it."):n.error,n.map))},[w,dt]),Vn=m.useCallback((e,t,o,n="view")=>{if(!i||!c)return;const r={mode:n,initialInstruction:sa.current.get(i)??yn(`videobook.image-edit-instruction:${i}`),key:[i,c.id,e.id,t.artifactId,t.objectHash].join(":"),bookId:i,notebookId:c.id,cellId:e.id,address:Se(e.slot),asset:t,returnFocus:o??(document.activeElement instanceof HTMLElement?document.activeElement:null),subjectMap:null,subjectMapLoading:t.type==="image"&&!!t.objectHash};rp(document.querySelector(".command-composer")),at.current+=1,gt(null),Vt(null);const s=We.current+1;We.current=s,Ar(null),_r(!1),No(r),me(!0),t.type==="image"&&Jo.ensureLoaded(i),!(t.type!=="image"||!t.objectHash)&&w("get_image_subject_map",{book_id:i,artifact_id:t.artifactId,object_hash:t.objectHash},{background:!0}).then(a=>{if(We.current!==s)return;const l=Fs(r,a);dt(r.key,l),l.status==="analyzing"&&On(r,s,l)}).catch(a=>{We.current===s&&dt(r.key,Ds(r,a))})},[i,w,Jo,c,dt,On]),Kt=m.useCallback(()=>{at.current+=1,gt(null),Vt(null),We.current+=1,Ar(null),_r(!1),No(null)},[]),yd=async(e,t)=>{const o=D(await w("extract_notebook_frame",{book_id:e.bookId,notebook_id:e.notebookId,source_cell_id:e.cellId,frame_mode:"time",timestamp_seconds:Math.round(t*1e3)/1e3})),n=_(o?.cell_id),r=_(o?.address),s=_(o?.run_id),a=_(o?.job_id);if(!n||!r||!s||!a)throw new Error("The server did not return the frame extraction cell");return ae(),ne(n,null),oe(n,!0),Pt({bookId:e.bookId,notebookId:e.notebookId,cellId:n,address:r.replace(/^@/,""),runId:s,jobOperationId:a,intervalMs:wn,timeoutMs:hn,maxPollFailures:fr}).then(l=>{if(l.kind==="failed"||l.kind==="timeout"){const u=l.message??`Frame extraction into ${r} failed`;ne(n,u),h(u,"error")}}).finally(()=>{oe(n,!1)}),r},Id=m.useCallback(async(e,t=!1)=>{if(!e.asset.objectHash)throw new Error("This image does not expose an immutable object hash");if(!ur({provider:"kie",model:"seedream/5-pro-layer-decomposition",tool:"analyze_image_subjects"}))return;const o=We.current+1;We.current=o,dt(e.key,{status:"analyzing",artifactId:e.asset.artifactId,objectHash:e.asset.objectHash,width:e.asset.width,height:e.asset.height,baseUrl:e.subjectMap?.baseUrl??null,jobId:null,startedAt:new Date().toISOString(),error:null,subjects:e.subjectMap?.subjects??[]},!0);try{const n=await w("analyze_image_subjects",{book_id:e.bookId,artifact_id:e.asset.artifactId,object_hash:e.asset.objectHash,...t?{force:!0}:{}});if(We.current!==o)return;const r=Fs(e,n);dt(e.key,r),r.status==="analyzing"&&On(e,o,r)}catch(n){throw We.current===o&&dt(e.key,Ds(e,n)),n}},[w,dt,On]),Gn=m.useCallback(async(e,t,o)=>{if(!e.asset.objectHash)throw new Error("This image does not expose an immutable object hash");if(i!==e.bookId)throw new Error("The active book changed while the image editor was open");if(Q.current.notebookId!==e.notebookId)throw new Error("The active notebook changed while the image editor was open");const n=t.model??sp,r=n.startsWith("fal-ai/")||n.startsWith("alibaba/")?"fal":"kie";if((t.operation!=="remove"||(t.editRegions?.length??0)>0)&&!ur({provider:r,model:n,tool:"edit_image_subjects"}))return!1;const s=We.current,a=()=>{const v=Q.current;return We.current===s&&v.bookId===e.bookId&&v.notebookId===e.notebookId},l=await Yi(async()=>await w("edit_image_subjects",{book_id:e.bookId,notebook_id:e.notebookId,source_cell_id:e.cellId,artifact_id:e.asset.artifactId,object_hash:e.asset.objectHash,...t.subjectIds.length>0?{subject_ids:t.subjectIds}:{},operation:t.operation,...t.model?{model:t.model}:{},...t.prompt?{prompt:t.prompt}:{},...t.editRegions?.length?{edit_regions:t.editRegions}:{},...t.regions&&t.regions.length>0?{regions:t.regions.map(v=>({replacement_artifact_id:v.replacementArtifactId,...v.box?{box:v.box}:{},...v.subjectId?{subject_id:v.subjectId}:{},...v.note?{note:v.note}:{}}))}:{}},{chat:o}),a);if(l.kind==="stale")return!1;if(l.kind==="error")throw l.error;const u=l.value,d=_(D(u)?.status)??"queued";M(o,()=>h(t.operation==="remove"?`${t.editRegions?.length?"Region":"Subject"} removal ${d}`:t.operation==="replace"?`Region replacement ${d}`:t.operation==="whole_image"?`Whole-image edit ${d}`:`${t.editRegions?.length?"Region":"Subject"} edit ${d}`)),await F(e.bookId,e.notebookId,a,o).catch(()=>{});const p=_(D(u)?.producer_cell_id);return p&&a()&&M(o,()=>{Kt(),Z(p,o),Le(null),kt(null),ae(o),ao(p)}),!0},[i,w,Kt,ae,F,ao,Z,h]),vo=m.useCallback(async()=>{const e=await w("list_books",{sort:"newest"}),t=ap(e);return j(t),t},[w]),Cd=m.useCallback(async(e,t=!1)=>{const o=`@${e.id}`;if(e.owningBookId!==i)return h(`Open ${e.owningBookName} to forget ${o}`,"error"),{ok:!1,message:`Open ${e.owningBookName} first`};if(!t&&!window.confirm(ip(o)))return{ok:!1,message:"Forget cancelled"};T(!0);try{let n=el(await w("delete_asset",{book_id:i,asset_id:e.artifactId,forget:!0}));if(n.status==="in_use"){if(!window.confirm(Es(o,n.references)))return{ok:!1,message:"Forget cancelled; media is still in use"};n=el(await w("delete_asset",{book_id:i,asset_id:e.artifactId,forget:!0,clear_references:!0}))}return n.status==="in_use"?(h(Es(o,n.references).split(`
|
|
8
|
+
Continue and remember this choice on this device?`)?(window.localStorage.setItem(Vl,"accepted"),!0):!1}const Xb=typeof window>"u"?"http://localhost/mcp":new URL("/mcp",window.location.origin).toString(),wn=500,hn=5*6e4,fr=10,Qb=5,Yb=1e3,Zb=2e3,ew=45*6e4,Gl=5e3,tw=3e3,ow=20*6e4,Ul=750,nw=20,Wl=45*6e4,rw=new Set(["queued","running","completing"]),sw=[];function rt(f){return new Promise(k=>window.setTimeout(k,f))}const aw=[{id:"jobs",label:"Jobs",icon:wb},{id:"settings",label:"Settings",icon:hb}];function zl(f,k){return!!(k==="transcript"?f?.transcript:f?.visionAnalysis)}function iw(f){return Wp(f)}function Gs(f){return f==="generate_audio"?"audio":f==="generate_image"?"image":"video"}function Hl(f){const k=f.document.cells.find(g=>g.id===f.sourceCellId);if(!k)throw new Error("The source asset cell is no longer available");return Ql({actions:f.actions,cellId:f.cellId,command:{cellType:f.cellType,mediaKind:Gs(f.cellType),prompt:"",sourceReferences:[W(k.slot)]},document:f.document,fallbackSlot:Mo(f.cellType,f.document.cells,f.lastWorkSlot),lastWorkSlot:f.lastWorkSlot})}function pt(f){return{ok:!0,message:f,nextInput:"/apply",selectInput:!0}}function Bl(f){return{ok:!0,message:f,nextInput:"/apply ",selectInput:!1}}function Kl(f){return f.match(/https?:\/\/[^\s]+/u)?.[0]??f}function vn(f){return{ok:!1,error:f instanceof Error?f.message:String(f)}}function Fs(f,k){const g=zp(k);if(g.artifactId&&g.artifactId!==f.asset.artifactId)throw new Error("The subject map belongs to another image artifact");if(g.objectHash&&g.objectHash!==f.asset.objectHash)throw new Error("The image changed before subject analysis finished");return{...g,artifactId:g.artifactId??f.asset.artifactId,objectHash:g.objectHash??f.asset.objectHash??null,width:g.width??f.asset.width,height:g.height??f.asset.height}}function Ds(f,k,g=f.subjectMap){return{status:"failed",artifactId:f.asset.artifactId,objectHash:f.asset.objectHash??null,width:f.asset.width,height:f.asset.height,baseUrl:g?.baseUrl??null,jobId:g?.jobId??null,startedAt:g?.startedAt??null,error:k instanceof Error?k.message:String(k),subjects:g?.subjects??[]}}function lw(f,k){if(!f||!k)return null;const g=pr(k),b=f.tracks.filter(I=>I.trackId.toLowerCase().startsWith(g)||I.name.toLowerCase()===g);return b.length===1?b[0]:null}function ec(f,k){const g=f.tracks.filter(I=>I.kind==="audio"&&I.enabled&&!I.locked&&!I.muted);return g.find(I=>{const x=f.clips.filter(j=>j.trackId===I.trackId);return x.length===1&&x[0]?.timelineStartFrame===0&&x[0].source.kind==="timed"&&x[0].source.artifactId===k})??g.find(I=>!f.clips.some(x=>x.trackId===I.trackId))??null}function cw(f,k,g){const b=ec(f,k);if(!b)return!1;const I=f.clips.filter(j=>j.trackId===b.trackId),x=I[0];return I.length===1&&x!==void 0&&x.timelineStartFrame===0&&x.durationFrames===g&&x.source.kind==="timed"&&x.source.artifactId===k}function dw(f,k,g){const b=f.stages.find(i=>i.kind==="edit"),I=b?.intent.operations.find(i=>i.kind==="insert-clip"&&i.placement.source.artifactId===g);if(I?.kind==="insert-clip")return I.placement.durationFrames;const x=k.clips.find(i=>i.timelineStartFrame===0&&i.source.kind==="timed"&&i.source.artifactId===g),j=b?.intent.operations.find(i=>i.kind==="trim-clip"&&i.clipId===x?.clipId);if(j?.kind==="trim-clip")return j.durationFrames;if(x)return x.durationFrames;throw new Error("The soundtrack setup plan has no duration boundary")}function uw(f){const k=f.stages.flatMap(I=>I.kind==="edit"?I.intent.operations:[]),g=k.filter(I=>I.kind==="insert-clip").length,b=k.filter(I=>I.kind==="set-clip-audio"?I.audio.muted:I.kind==="set-clip-speed"&&I.audioPolicy==="mute").length;return`${g>0?"Place":"Normalize"} master soundtrack · mute ${b} other ${b===1?"clip":"clips"}`}function Jl(f){return f.valid?null:f.conflicts.map(g=>g.message).join(" · ")||"The canonical edit preview is invalid"}function fw(f){const g=f.find(b=>b.kind==="edit")?.intent.operations.map(b=>{if(b.kind==="insert-clip")return{kind:"insert",mode:b.mode,artifact_id:b.placement.source.artifactId,track_id:b.placement.trackId,timeline_start_frame:b.placement.timelineStartFrame,duration_frames:b.placement.durationFrames,...b.placement.source.kind==="timed"?{source_start_tick:b.placement.source.range.startTick,source_duration_ticks:b.placement.source.range.durationTicks}:{}};if(b.kind==="trim-clip")return{kind:"trim",clip_id:b.clipId,timeline_start_frame:b.timelineStartFrame,duration_frames:b.durationFrames};if(b.kind==="set-clip-audio")return{kind:"volume",clip_id:b.clipId,gain_db:b.audio.gainDb,muted:b.audio.muted,fade_in_frames:b.audio.fadeInFrames,fade_out_frames:b.audio.fadeOutFrames};if(b.kind==="move-clip")return{kind:"move",clip_id:b.clipId,track_id:b.trackId,timeline_start_frame:b.timelineStartFrame};if(b.kind==="split-clip")return{kind:"split",clip_id:b.clipId,split_frame:b.splitFrame};if(b.kind==="set-clip-transform")return{kind:"transform",clip_id:b.clipId,fit:b.transform.fit,position_x:b.transform.positionX,position_y:b.transform.positionY,scale_x:b.transform.scaleX,scale_y:b.transform.scaleY,rotation_degrees:b.transform.rotationDegrees,opacity:b.transform.opacity,crop_top:b.transform.cropTop,crop_right:b.transform.cropRight,crop_bottom:b.transform.cropBottom,crop_left:b.transform.cropLeft};if(b.kind==="set-clip-speed")return{kind:"speed",clip_id:b.clipId,numerator:b.speed.numerator,denominator:b.speed.denominator,reverse:b.reverse,audio_policy:b.audioPolicy};if(b.kind==="set-transition")return{kind:"transition",outgoing_clip_id:b.outgoingClipId,incoming_clip_id:b.incomingClipId,transition_kind:b.transition?.kind??null,...b.transition?{duration_frames:b.transition.durationFrames,alignment:b.transition.alignment}:{}};if(b.kind==="upsert-caption-cue")return{kind:"caption",cue_id:b.cue.cueId,track_id:b.cue.trackId,timeline_start_frame:b.cue.timelineStartFrame,duration_frames:b.cue.durationFrames,text:b.cue.text,style_id:b.cue.styleId,...b.cue.speaker?{speaker:b.cue.speaker}:{}};throw new Error(`The edit cannot be replanned: ${b.kind}`)})??[];if(g.length===0)throw new Error("The plan has no editable operation");return g.length===1?g[0]:g}function yn(f){try{return window.localStorage.getItem(f)??""}catch{return""}}function Ot(f,k){try{window.localStorage.setItem(f,k)}catch{return}}const mr={offset:0,limit:24,total:0,hasMore:!1};function Os(f){return f==="final"?"video":f==="audio"||f==="image"||f==="video"?f:null}function mw(f){return f==="all"?["audio","image","video","final"]:f==="video"?["video","final"]:[f]}function Vs(f,k){return mw(f).includes(k)}async function Xl(f){const k=await window.crypto.subtle.digest("SHA-256",await f.arrayBuffer());return[...new Uint8Array(k)].map(g=>g.toString(16).padStart(2,"0")).join("")}function pw(f){return`slot-context-menu-${f.row}-${f.column}`}const gw={cell:Lf,timeline:Nf,goal:ub},kw={busRiver:qf},bw={hideAttribution:!0},ww={selectable:!1},hw=["Shift","Control","Meta"],vw=[];function yw({initialWorkspace:f}){const k=m.useMemo(()=>zf(f),[f]),g=Hf({url:Xb,clientName:"videobook",reconnectDelayMs:3e3}),[b,I]=m.useState(()=>Ni(window.location.pathname)),[x,j]=m.useState(()=>k?.books??[]),[i,K]=m.useState(()=>k?.bookId??yn("videobook.active-book")),[c,xe]=m.useState(()=>k?.notebook??null),[H,Je]=m.useState(()=>k?.assets??[]),[J,Ee]=m.useState(()=>k?.sequence??null),[Ve,Ws]=m.useState(()=>k?.jobs??[]),[tc,zs]=m.useState(()=>Date.now()),[In,oc]=m.useState(()=>k?.commands??[]),[Et,kr]=m.useState([]),[br,wr]=m.useState({loading:!1,error:null}),[qe,Xe]=m.useState(null),at=m.useRef(0),To=m.useRef(0),[hr,gt]=m.useState(null),[Cn,Vt]=m.useState(null),[nc,rc]=m.useState(null),[sc,ac]=m.useState(null),[Ne,jo]=m.useState(null),Hs=m.useRef(null),[vr,ic]=m.useState(()=>k?.chatModelCatalog??Li),[Bs,Ks]=m.useState(()=>Is(k?.chatModelCatalog??Li,yn("videobook.chat-model"))),[Qe,Js]=m.useState(()=>k?.generationActions??[]),lc=m.useMemo(()=>new Map(Qe.map(e=>[e.model,e.title])),[Qe]),[cc,dc]=m.useState([]),[$o,so]=m.useState(Bf),Sn=Zn($o.status),[uc,yr]=m.useState(null),[fc,Xs]=m.useState(!1),[mc,Qs]=m.useState(null),[pc,Ys]=m.useState(!1),Zs=m.useRef(0),{lastWorkSlot:Ge,rememberLastWorkSlot:Ae}=Kf(i,c?.id??null),[Me,qo]=m.useState(null),[xn,gc]=m.useState(()=>new Set),[Ye,En]=m.useState(null),[An,ea]=m.useState(()=>new Set),[Ir,Cr]=m.useState(()=>new Set),[Sr,ta]=m.useState(()=>new Set),[xr,oa]=m.useState({}),[na,kc]=m.useState({}),[ao,ra]=m.useState({}),[z,ke]=m.useState(null),fe=Jf(),[he,Te]=m.useState(null),[Y,No]=m.useState(null),sa=m.useRef(new Map),[ve,Ue]=m.useState(null),[it,Er]=m.useState(null),[bc,Ar]=m.useState(null),[aa,_r]=m.useState(!1),[Lo,Gt]=m.useState(null),[ia,Fo]=m.useState(!1),[wc,hc]=m.useState(null),{scrollRef:Ut,surface:At,zoom:je,revealCell:io}=Xf(i,c?.id,b==="notebook"),[la,vc]=m.useState(58),[ca,yc]=m.useState(58),Ic=m.useMemo(()=>({"--notebook-command-row-height":`${la}px`,"--notebook-composer-height":`${ca}px`}),[la,ca]),[Rr,me]=m.useState(!1),[Wt,Le]=m.useState(null),[zt,kt]=m.useState(null),[lo,_n]=m.useState(null),[Cc,Pr]=m.useState(!1),[Sc,Mr]=m.useState(!1),[xc,Tr]=m.useState(null),[Ec,da]=m.useState(!1),[ue,le]=m.useState(null),[E,O]=m.useState(null),jr=m.useRef(null),ua=m.useRef(null),$r=m.useRef(!1),[qr,co]=m.useState(""),[G,T]=m.useState(!1),{turns:fa,begin:ma,observe:Rn,cancelReview:pa,claimVoice:ga}=Qf(i,c?.id??null),ka=m.useRef(void 0),[Ac,_c]=m.useState(null),[Rc,Nr]=m.useState(Yf),[Pc,ba]=m.useState(null),[_t,Mc]=m.useState(()=>window.navigator.onLine),[Ht,Do]=m.useState({text:"Connect to the server, then load your books.",tone:"info"}),h=m.useCallback((e,t="info")=>{Do({text:e,tone:t})},[]),Oo=m.useRef(null),Vo=m.useRef(0),_e=m.useRef(0),We=m.useRef(0),Lr=m.useRef(0),Fr=m.useRef(null),Ze=m.useRef(new Map),Go=m.useRef(new Map),Dr=m.useRef(0),Pn=m.useRef(new Map),lt=m.useRef(new Set),Q=m.useRef({bookId:i,notebookId:c?.id??null,assets:H}),Pe=m.useRef(async()=>{throw new Error("MCP call is not ready")}),ye=m.useRef(0),Or=m.useRef(Ve),wa=m.useRef(b),ne=m.useCallback((e,t)=>{ra(o=>{if(t===null){if(!(e in o))return o;const n={...o};return delete n[e],n}return o[e]===t?o:{...o,[e]:t}})},[]);m.useEffect(()=>{if(!Ht||Ht.tone!=="info")return;const e=Ht,t=window.setTimeout(()=>{Do(o=>o===e?null:o)},6e3);return()=>window.clearTimeout(t)},[Ht]);const uo=m.useMemo(()=>x.find(e=>e.bookId===i)??null,[i,x]),re=m.useMemo(()=>new Map(H.map(e=>[e.artifactId,e])),[H]),se=m.useMemo(()=>Zf(c?.cells??[],H),[H,c]),Vr=m.useMemo(()=>em(c?.cells??[],H),[H,c]),Uo=m.useMemo(()=>[...Vr.values()].flatMap(e=>e.asset?[{...e.asset,cellAddress:e.token.slice(1)}]:[]),[Vr]),U=E?.kind==="generation"?E.draft:null,ha=m.useMemo(()=>{if(E?.kind!=="routed")return null;const e=E.plan;if(e.routedTool!=="change_video_speed")return null;const t=_(e.params.asset_id),o=t?se.find(p=>p.artifactId===t):void 0,n=t?re.get(t):void 0,r=ie(n?.duration)??ie(o?.duration),s=ie(e.params.speed),a=ie(e.params.target_duration_seconds),l=s??(r&&a&&a>0?r/a:null),u=n?.mediaUrl??null,d=n?.type??o?.type??null;return{mediaUrl:u,thumbnailUrl:n?.thumbnailUrl??null,unavailableReason:d!==null&&d!=="video"?"the selected source is not a video":u===null?"the source media is not loaded yet":null,sourceDurationSeconds:r&&r>0?r:null,effectiveSpeed:l&&l>0?l:null}},[re,se,E]),Tc=E?.kind==="routed"?tm({input:E.plan.prompt,params:E.plan.params,tool:E.plan.routedTool,sourceDurationSeconds:ha?.sourceDurationSeconds??null}):null,fo=m.useMemo(()=>{if(E?.kind!=="routed")return null;const e=E.plan;if(e.tool!=="post"&&e.routedTool!=="post")return null;const t=_(e.params.asset_id)?.trim()??"",o=t.replace(/^@/,""),n=se.find(u=>u.artifactId===o||u.cellAddress.toLowerCase()===o.toLowerCase()),r=re.get(n?.artifactId??o)??n??null,s=Fi(e.params),a=E.xPostReview,l=a?.options.enabled&&to(a).length===0?{blocking:Di,notice:null}:om(s,void 0,Sn);return{asset:r,draft:s,error:Oi(s,void 0,Sn),validation:l,sourceLabel:n?`@${n.cellAddress}`:t.startsWith("@")?t:o?`@${o}`:"Selected media"}},[re,se,E,Sn]),bt=m.useMemo(()=>U&&c?nm(U,c):[],[c,U]),Wo=m.useMemo(()=>U?rm(Qe,U.cell.type,bt):[],[Qe,bt,U]),jc=m.useMemo(()=>U?sm(U.action,bt):[],[bt,U]),zo=m.useMemo(()=>U&&c?U.sourceCellIds.flatMap(e=>{const t=c.cells.find(o=>o.id===e);return t?[{cellId:e,address:Se(t.slot),type:t.type,asset:t.outputArtifactId?re.get(t.outputArtifactId)??null:null}]:[]}):[],[re,c,U]),Ho=m.useMemo(()=>{if(!E)return Cs;if(E.kind==="generation"&&U)return{target:Se(U.cell.slot),sources:zo.map(e=>e.address)};if(E.kind==="frame"||E.kind==="split")return{target:null,sources:E.expectations.map(e=>e.address)};if(E.kind==="notebook"){const[e,...t]=E.plan.expectations.map(o=>o.address);return{target:e??null,sources:t}}if(E.kind==="transcribe"&&E.assetId){const e=E.assetId,t=se.find(o=>o.artifactId===e)?.cellAddress;return t?{target:null,sources:[t]}:Cs}return Cs},[se,E,U,zo]),Gr=m.useMemo(()=>am(Ho),[Ho]),$c=m.useMemo(()=>U&&c?im(c,U.sourceCellIds,U.cell.id).map(({cell:e})=>({cellId:e.id,address:Se(e.slot),type:e.type,asset:e.outputArtifactId?re.get(e.outputArtifactId)??null:null})):[],[re,c,U]),Ur=m.useMemo(()=>lm(c?.generationPlans),[c]),w=m.useCallback(async(e,t,o)=>{if(g.state!=="ready")throw new Error("MCP server is not ready");if(o?.chat&&!o.chat.isInScope())throw new Error("Workspace changed. Repeat the command in the current workspace.");if(o?.background||!cm(e)){const l=Vi(await g.callTool(e,t));return o?.chat?.accept(e,t,l),l}const n=Vp(),r=performance.now();Go.current.set(n,{tool:e,startedAt:r}),Nr(l=>dm(l,{id:n,turnId:o?.chat?.visible===!1?void 0:o?.chat?.id,tool:e,args:um(t)}));let s="done",a="";try{const l=Vi(await g.callTool(e,t));return a=fm(l),o?.chat?.accept(e,t,l),l}catch(l){throw s="failed",a=l instanceof Error?l.message:String(l),l}finally{Go.current.delete(n);const l=performance.now()-r,u=()=>{Pn.current.delete(n),Nr(p=>Up(p,n,{phase:s,elapsedMs:l,detail:a})),!(Go.current.size>0)&&(window.clearTimeout(Dr.current),ba(s==="failed"?"error":"success"),Dr.current=window.setTimeout(()=>ba(null),s==="failed"?1100:620))},d=Math.max(0,Gp-l);d===0?u():Pn.current.set(n,window.setTimeout(u,d))}},[g]),Mn=E?.kind==="post-delivery"?E.review:null;mm(!!(Mn?.receipt&&Mn.destination==="icloud"),g.state==="ready"?w:void 0,Mn?.bookId??"",Mn?.postId??"",e=>O(t=>t?.kind==="post-delivery"?{...t,review:{...t.review,sync:e}}:t));const Bo=m.useMemo(()=>i&&c?{bookId:i,notebookId:c.id}:null,[i,c]),{goals:Wr,events:qc,accept:Nc,refresh:va,act:ya}=pm(w,Bo),zr=m.useMemo(()=>new Set((c?.cells??[]).filter(e=>e.type==="goal").map(e=>e.id)),[c]),Ko=m.useMemo(()=>Wr.filter(e=>zr.has(e.cellId)),[zr,Wr]),Ia=m.useMemo(()=>new Map(Ko.map(e=>[e.cellId,e])),[Ko]),Lc=m.useMemo(()=>gm(Ko),[Ko]),mo=km(Ko),Jo=bm({callTool:w,ready:g.state==="ready"}),Hr=wm({bookId:i,ready:g.state==="ready",call:w}),Fc=m.useCallback(async e=>{try{const t=D(await w("estimate_cost",{calls:[{tool_name:"edit_image_subjects",input:{model:e}}]})),o=D(t?.estimate),n=Array.isArray(o?.warnings)?o.warnings.filter(l=>typeof l=="string"):[],r=typeof o?.usd=="number"?o.usd:null,s=Gi(n);if(r===null||r<=0||n.length>0&&!s)return null;const a=`$${r.toFixed(r<.01?4:2)}`;return s?`${a} · historical average`:a}catch{return null}},[w]),[Xo,Tn]=m.useState(null),et=hm({bookId:i,ready:g.state==="ready"&&!G,sequence:J,call:w,parseSequence:Ke,parseAssets:Lt,onSequence:e=>{ye.current=performance.now(),Ee(e)},onAssets:e=>Je(t=>{const o=new Map(t.map(n=>[n.artifactId,n]));for(const n of e)o.set(n.artifactId,n);return[...o.values()]})}),wt=vm({bookId:i,ready:g.state==="ready",sequence:J,call:w,onSequence:e=>{const t=Ke(e);t&&(ye.current=performance.now(),Ee(t))}}),jn=Xo?.bookId===i?c?.cells.find(e=>e.id===Xo.cellId&&e.type==="timeline"):void 0,Qo=!!(jn&&J&&b==="notebook"),{preview:Ca,select:Yo}=ym({bookId:i,notebook:c,ready:g.state==="ready",call:w}),Dc=m.useCallback(e=>{Nr(t=>Im(t,e))},[]);m.useEffect(()=>()=>{window.clearTimeout(Dr.current);for(const e of Pn.current.values())window.clearTimeout(e);Pn.current.clear()},[]),m.useEffect(()=>{Pe.current=w},[w]),m.useEffect(()=>{Q.current={bookId:i,notebookId:c?.id??null,assets:H}},[H,i,c?.id]),m.useEffect(()=>{Or.current=Ve},[Ve]),m.useEffect(()=>{wa.current=b},[b]);const ct=m.useCallback(e=>{Rn(Q.current.bookId??"",e);const t=!Nt(Or.current,e);t&&(Or.current=e,Ws(e));const o=wa.current==="jobs"&&e.some(n=>rw.has(n.state));(t||o)&&zs(Date.now())},[Rn]),Rt=m.useCallback((e,t,o=null)=>{oa(n=>({...n,[e]:{operation:t,error:o}}))},[]),Zo=m.useCallback((e,t)=>{Rt(e,null,t)},[Rt]),oe=m.useCallback((e,t)=>{ea(o=>{const n=new Set(o);return t?n.add(e):n.delete(e),n.size===o.size?o:n})},[]),en=m.useCallback(e=>{Cr(t=>new Set([...t,...e])),window.setTimeout(()=>{Cr(t=>{const o=new Set(t);for(const n of e)o.delete(n);return o.size===t.size?t:o})},900)},[]),[Br,Sa]=m.useState(()=>new Set),po=m.useRef(null);m.useEffect(()=>()=>{po.current!==null&&window.clearTimeout(po.current)},[]);const go=m.useCallback((e,t={})=>{Sa(o=>Cm(o,e)),po.current!==null&&window.clearTimeout(po.current),po.current=window.setTimeout(()=>{po.current=null,Sa(o=>Sm(o,e))},xm),t.scroll&&window.requestAnimationFrame(()=>{if(t.scroll==="offscreen"&&Oo.current?.getNodes().some(n=>n.dragging))return;const o=window.matchMedia("(prefers-reduced-motion: reduce)").matches;for(const n of e){const r=document.querySelector(`[data-id="${n}"]`);if(r){if(t.scroll==="offscreen"){const s=r.getBoundingClientRect();if(s.top>=0&&s.left>=0&&s.bottom<=window.innerHeight&&s.right<=window.innerWidth)continue}r.scrollIntoView({block:"center",behavior:o?"auto":"smooth"})}}})},[]),ko=m.useCallback(()=>{Ui(()=>document.querySelector('.command-composer [aria-label="Videobook command input"]'))},[]);m.useEffect(()=>{const e=()=>Mc(window.navigator.onLine);return window.addEventListener("online",e),window.addEventListener("offline",e),()=>{window.removeEventListener("online",e),window.removeEventListener("offline",e)}},[]);const bo=m.useCallback(async(e,t,o)=>{if(!i||!c)throw new Error("Load a notebook first.");return ft(await w("plan_notebook_generation",{book_id:i,notebook_id:c.id,cell_id:e,source_surface:t,actor:"videobook-user",timeline_start_frame:0},{chat:o}))},[i,w,c]),Kr=m.useCallback(async(e,t,o)=>{const n=await bo(e,t,o);return L(o,!1,()=>O(null)),L(o,!0,()=>le({plan:n,previews:{}})),M(o,()=>ko()),pt("Generation plan ready for review")},[bo,ko]),[ze,ht]=m.useState(()=>k?.notebook?Ss(k.notebook,k.assets,k.jobs):[]),[xa,$n]=m.useState(()=>k?.notebook?Wi(k.notebook):[]),wo=m.useCallback(e=>{e.size>0&&ke(o=>o?.cellId===null?null:o);const t=lt.current;t.size===e.size&&[...e].every(o=>t.has(o))||(lt.current=e,gc(e))},[]),Z=m.useCallback((e,t,o)=>{if(t&&!t.isCurrent()||(_c(e?t?.id??null:null),qo(e),Yo(e,o),wo(e?new Set([e]):new Set),!e))return;const n=c?.cells.find(s=>s.id===e);if(n){Ae(n.slot);return}const r=ze.find(s=>s.id===e);r&&Ae(r.data.slot)},[Yo,c,ze,Ae,wo]),ho=m.useCallback(()=>{En(null)},[]),Ea=m.useCallback((e,t,o)=>{Z(e),En({target:{kind:"cell",cellId:e},position:t,returnFocus:o})},[Z]),Oc=m.useCallback((e,t,o)=>{En({target:{kind:"slot",slot:e},position:t,returnFocus:o})},[]),Bt=Ye?.target.kind==="cell"?Ye.target.cellId:null,Vc=m.useMemo(()=>({openCellId:Bt,open:Ea}),[Bt,Ea]),Ie=m.useCallback((e,t,o,n=i)=>{Rn(n,o,e,t),ye.current=performance.now(),xe(s=>Nt(s,e)?s:e);const r=new Set(e.cells.map(s=>s.id));ea(s=>{const a=new Set([...s].filter(l=>r.has(l)));return a.size===s.size?s:a}),Cr(s=>{const a=new Set([...s].filter(l=>r.has(l)));return a.size===s.size?s:a}),oa(s=>Object.keys(s).every(a=>r.has(a))?s:Object.fromEntries(Object.entries(s).filter(([a])=>r.has(a)))),ra(s=>Object.keys(s).every(a=>r.has(a))?s:Object.fromEntries(Object.entries(s).filter(([a])=>r.has(a)))),wo(new Set([...lt.current].filter(s=>r.has(s)))),ke(s=>s&&s.bookId===n&&s.notebookId===e.id&&(s.cellId===null||r.has(s.cellId))?s:null),En(s=>!s||s.target.kind==="slot"||r.has(s.target.cellId)?s:null),ht(s=>Em(s,Ss(e,t,o))),$n(s=>Am(s,Wi(e))),qo(s=>s&&e.cells.some(a=>a.id===s)?s:null),Le(s=>s&&r.has(s)?s:null)},[i,Rn,wo]);_m({bookId:i,notebookId:c?.id??null,enabled:g.state==="ready"&&b==="notebook"&&!G&&!et.busy&&!ze.some(e=>e.dragging),refresh:async e=>{if(g.state!=="ready"||!c||Go.current.size>0)return;const t=performance.now(),o=zr.size>0||Wr.length>0,[n,r,s,a,l]=await Promise.allSettled([w("get_notebook",{book_id:i,notebook_id:c.id},{background:!0}),w("list_assets",{book_id:i,sort:"newest",limit:200,include_referenced:!0},{background:!0}),w("list_jobs",{book_id:i,limit:200},{background:!0}),c.cells.some(v=>v.type==="timeline")?w("get_primary_sequence",{book_id:i},{background:!0}):Promise.resolve(null),o?w("video_goal",{book_id:i,notebook_id:c.id,action:"list"},{background:!0}):Promise.resolve(null)]);if(!e()||Go.current.size>0||(l.status==="fulfilled"&&l.value&&Nc({bookId:i,notebookId:c.id},l.value),t<ye.current)||n.status!=="fulfilled"||r.status!=="fulfilled"||s.status!=="fulfilled")return;const u=ge(n.value);if(!u)return;const d=Lt(r.value),p=oo(s.value);if(Je(v=>Nt(v,d)?v:d),a.status==="fulfilled"&&a.value){const v=Ke(a.value);v&&Ee(S=>Nt(S,v)?S:v)}ct(p),Ie(u,d,p)}});const Pt=m.useCallback(async e=>{Ze.current.set(e.cellId,e.runId);let t=!1,o=0;const n=Date.now()+e.timeoutMs,r=()=>{const l=Q.current;return l.bookId===e.bookId&&l.notebookId===e.notebookId},s=async()=>{const l=performance.now(),[u,d,p]=await Promise.all([Pe.current("get_notebook",{book_id:e.bookId,notebook_id:e.notebookId},{background:!0}),Pe.current("list_assets",{book_id:e.bookId,sort:"newest",limit:200,include_referenced:!0},{background:!0}),Pe.current("list_jobs",{book_id:e.bookId,limit:200},{background:!0})]);if(!r())return;const v=ge(u);if(!v)return;const S=Lt(d),A=oo(p);l<ye.current||(ye.current=l,Je(y=>Nt(y,S)?y:S),ct(A),Ie(v,S,A))},a=async()=>{for(let l=0;l<Qb;l+=1){if(!r())return;try{await s();return}catch{await rt(Yb)}}};try{for(;Date.now()<n;){if(Ze.current.get(e.cellId)!==e.runId)return{kind:"superseded"};const l=Q.current;if(l.bookId!==e.bookId||l.notebookId!==e.notebookId)return{kind:"superseded"};try{const u=performance.now(),[d,p]=await Promise.all([Pe.current("get_notebook",{book_id:e.bookId,notebook_id:e.notebookId},{background:!0}),Pe.current("list_jobs",{book_id:e.bookId,limit:200},{background:!0})]);o=0;const v=Q.current;if(v.bookId!==e.bookId||v.notebookId!==e.notebookId||Ze.current.get(e.cellId)!==e.runId)return{kind:"superseded"};const S=ge(d);if(!S)throw new Error("The server returned an invalid notebook");const A=oo(p),y=u>=ye.current;y&&(ye.current=u,ct(A));const R=A.map(zi),q=Rm({jobs:R,cellId:e.cellId,runId:e.runId,jobOperationId:e.jobOperationId}),V=Pm(S,e.cellId,e.runId);V.state!=="pending"&&oe(e.cellId,!1),y&&Ie(S,v.assets,A);const X=Mm({observation:V,job:q,address:e.address,sawRun:t});if(X.kind==="continue"){t=X.sawRun,await rt(e.intervalMs);continue}return X.kind==="completed"?(await a(),ne(e.cellId,null),{kind:"completed"}):X.kind==="failed"?{kind:"failed",message:X.message}:{kind:"superseded"}}catch(u){if(o+=1,o>=e.maxPollFailures){const d=u instanceof Error?u.message:String(u);return await a(),{kind:"failed",message:`Lost contact with the server while watching @${e.address}: ${d}`}}await rt(e.intervalMs)}}return await a(),{kind:"timeout"}}finally{Ze.current.get(e.cellId)===e.runId&&Ze.current.delete(e.cellId)}},[ct,Ie,oe,ne]),tn=m.useCallback(async(e,t)=>{try{const o=await Pt({...e,intervalMs:Zb,timeoutMs:ew,maxPollFailures:10});if(o.kind==="completed"){M(t,()=>{h(`@${e.address} generated`),go([e.cellId],{scroll:"offscreen"})}),ne(e.cellId,null);return}if(o.kind==="failed"){const n=o.message??`@${e.address} failed`;ne(e.cellId,n),M(t,()=>h(n,"error"));return}o.kind==="timeout"&&M(t,()=>h(`@${e.address} is still running — check the Jobs screen`))}catch(o){const n=o instanceof Error?o.message:String(o);ne(e.cellId,n),M(t,()=>h(n,"error"))}finally{oe(e.cellId,!1)}},[go,oe,ne,h,Pt]),qn=m.useCallback(async e=>{const t=e.intervalMs??Gl,o=`${e.tokenPrefix??"media"}:${e.artifactId}`;Ze.current.set(e.cellId,o);let n=e.artifactId,r=0;const s=Date.now()+Wl;try{for(;Date.now()<s;){const a=Q.current;if(Ze.current.get(e.cellId)!==o||a.bookId!==e.bookId||a.notebookId!==e.notebookId)return;try{const l=performance.now(),[u,d,p]=await Promise.all([Pe.current("get_notebook",{book_id:e.bookId,notebook_id:e.notebookId},{background:!0}),Pe.current("list_assets",{book_id:e.bookId,sort:"newest",limit:200,include_referenced:!0},{background:!0}),Pe.current("list_jobs",{book_id:e.bookId,limit:200},{background:!0})]);r=0;const v=Q.current;if(Ze.current.get(e.cellId)!==o||v.bookId!==e.bookId||v.notebookId!==e.notebookId)return;const S=ge(u);if(!S)throw new Error("The server returned an invalid notebook");const A=S.cells.find(V=>V.id===e.cellId);if(!A||A.outputArtifactId!==n)return;const y=Lt(d),R=oo(p);l>=ye.current&&(ye.current=l,Je(V=>Nt(V,y)?V:y),ct(R),Ie(S,y,R));const q=Tm(n,y.find(V=>V.artifactId===n),R,jm(S,e.cellId));if(q.kind==="redirected"){const V=y.find(P=>P.artifactId===q.artifactId),X=V?Os(V.type):null;if(!V||!X){await rt(t);continue}await Pe.current("update_notebook_cell",{book_id:e.bookId,notebook_id:e.notebookId,cell_id:e.cellId,cell:{type:X,output_artifact_id:V.artifactId}},{background:!0}),n=V.artifactId,ne(e.cellId,null);continue}if(q.kind==="completed"){ne(e.cellId,null),e.completedNotice&&h(e.completedNotice);return}if(q.kind==="failed"){ne(e.cellId,q.message),h(q.message,"error");return}await rt(t)}catch(l){if(r+=1,r>=10){const u=l instanceof Error?l.message:String(l);h(`Stopped watching @${e.address}: ${u}. Check the Jobs screen.`,"error");return}await rt(t)}}h(e.stillWorkingNotice??`@${e.address} is still processing — check the Jobs screen`)}finally{Ze.current.get(e.cellId)===o&&Ze.current.delete(e.cellId)}},[ct,Ie,ne,h]),Gc=m.useCallback(async e=>{await qn({...e,tokenPrefix:"download",intervalMs:Gl,completedNotice:`@${e.address} downloaded`,stillWorkingNotice:`@${e.address} is still downloading — check the Jobs screen`})},[qn]),Nn=m.useCallback(async e=>{await qn({...e,tokenPrefix:"process",intervalMs:Ul,stillWorkingNotice:`@${e.address} is still processing — check the Jobs screen`})},[qn]),Ln=m.useCallback((e,t,o)=>{const n=new Map(o.map(r=>[r.artifactId,r]));for(const r of t.cells){if(!Ft(r.type)||!r.outputArtifactId)continue;const s=n.get(r.outputArtifactId);!s||s.status==="ready"||s.status==="error"||Ze.current.has(r.id)||Nn({bookId:e,notebookId:t.id,cellId:r.id,address:Se(r.slot),artifactId:r.outputArtifactId})}},[Nn]),Aa=m.useRef(!1);m.useEffect(()=>{Aa.current||!i||!c||(Aa.current=!0,Ln(i,c,H))},[H,i,c,Ln]);const ae=m.useCallback(e=>{const t=Q.current;t.bookId!==i||t.notebookId!==c?.id||$r.current||M(e,()=>me(!1))},[i,c?.id]),on=m.useCallback(async(e,t,o,n)=>{if(!i||!c)return;let r=!1;T(!0),ne(e,null);try{const s=t??ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(!s)throw new Error("The server returned an invalid notebook");const a=s.cells.find(S=>S.id===e);if(!a||!iw(a))throw new Error("Configure this cell before running it");const l=$m(a);if(l&&!_t)throw new Error("Offline: cloud generation is unavailable. Local search, editing, playback, and export remain available.");if(l){if(Hi(a)){const A=await bo(e,"ui",o),y=A.stages.find(de=>de.kind==="queued"&&de.jobType==="generation"&&de.tool==="run_notebook_cell"&&de.input.cell_id===e);if(y?.kind!=="queued")throw new Error("The generation plan is missing its notebook cell");const R=_(y.input.notebook_id);if(R!==s.id)throw new Error("The generation plan belongs to another notebook");if(!ur(y))throw new Error("Cloud generation cancelled before sending data");L(o,!1,()=>O(null)),L(o,!1,()=>le(null));const q=await er({start:()=>w("run_notebook_cell",{book_id:i,notebook_id:R,cell_id:e,plan:A,...n?{retry_failed_cell_id:n}:{},actor:"videobook-user"},{chat:o}),onStarting:()=>oe(e,!0),onAccepted:()=>oe(e,!1),onRejected:()=>oe(e,!1)}),V=D(q),X=_(V?.run_id),P=_(V?.job_id),N=_(V?.output_cell_id);if(!X||!P)throw oe(e,!1),new Error("The server did not return a notebook run");r=!0,N&&ae(o);const B=N??e;let te=Se(a.slot);if(N){const de=await w("get_notebook",{book_id:i,notebook_id:R},{background:!0,chat:o}),pe=ge(de);if(pe){Ie(pe,H,Ve);const Be=pe.cells.find(be=>be.id===N);Be&&(te=Se(Be.slot))}M(o,()=>en([N])),ne(N,null),oe(N,!0),lt.current.has(e)&&(Z(null,o),M(o,()=>go([N],{scroll:"center"})))}return M(o,()=>h(`${W(a.slot)} queued`)),tn({bookId:i,notebookId:R,cellId:B,address:te,runId:X,jobOperationId:P},o),{ok:!0,message:`${W(a.slot)} queued`}}const S=await Kr(e,"ui",o);return M(o,()=>h(S.message,S.ok?"info":"error")),S}const u=await er({start:()=>w("run_notebook_cell",{book_id:i,notebook_id:s.id,cell_id:e,actor:"videobook-user",...s.revision?{expected_revision:s.revision}:{}},{chat:o}),onStarting:()=>oe(e,!0),onRejected:()=>oe(e,!1)}),d=_(D(u)?.run_id),p=_(D(u)?.job_id);if(!d||!p)throw new Error("The server did not return a notebook run");M(o,()=>h(`${W(a.slot)} queued`));const v=await Pt({bookId:i,notebookId:s.id,cellId:e,address:Se(a.slot),runId:d,jobOperationId:p,intervalMs:wn,timeoutMs:hn,maxPollFailures:fr});if(v.kind==="failed")throw new Error(v.message??`${W(a.slot)} failed`);if(v.kind==="timeout")throw new Error("Notebook run did not finish within five minutes");return v.kind==="completed"&&M(o,()=>h(`${W(a.slot)} updated`)),{ok:!0,message:`${W(a.slot)} run accepted`}}catch(s){const a=s instanceof Error?s.message:String(s);return ne(e,a),M(o,()=>h(a,"error")),{ok:!1,message:a}}finally{r||oe(e,!1),T(!1)}},[Ie,H,i,w,ae,bo,go,Ve,c,_t,Kr,en,Z,oe,ne,h,tn,Pt]),Mt=m.useMemo(()=>{let e=ze;for(const t of An)e=qm(e,t,"queued");return Ir.size>0&&(e=e.map(t=>Ir.has(t.id)?{...t,data:{...t.data,revealing:!0}}:t)),Br.size>0&&(e=e.map(t=>Br.has(t.id)?{...t,data:{...t.data,highlighted:!0}}:t)),Object.keys(ao).length===0?e:e.map(t=>{const o=ao[t.id];return o?{...t,data:{...t.data,status:"error",statusError:o}}:t})},[ao,Br,ze,An,Ir]),Uc=m.useMemo(()=>Mt.map(e=>{const t=xn.has(e.id),o=Gr.get(Se(e.data.slot)),n=o?`notebook-review-${o}`:void 0;return e.selected===t&&e.className===n?e:{...e,selected:t,className:n}}),[Gr,Mt,xn]),Wc=m.useMemo(()=>Nm(xa,Me),[xa,Me]),vt=m.useMemo(()=>ze.flatMap(e=>Tl({type:e.data.kind,slot:e.data.slot})),[ze]),_a=m.useMemo(()=>ze.map(e=>({type:e.data.kind,slot:e.data.slot})),[ze]),Jr=m.useMemo(()=>Bi(vt,{viewportWidth:At.width,viewportHeight:At.height,zoom:je}),[vt,At.height,At.width,je]),Tt=m.useMemo(()=>Lo?Bi(vt,{preview:Lo,viewportWidth:At.width,viewportHeight:At.height,zoom:je}):Jr,[vt,Jr,At.height,At.width,je,Lo]),Fn=m.useMemo(()=>Lm(Tt,je),[Tt,je]),zc=m.useMemo(()=>Fm(Dm(_a,Tt.rowCount)),[_a,Tt.rowCount]),Hc=m.useMemo(()=>({"--notebook-detail-scale":Ki(je),width:Fn.width,height:Fn.height}),[Fn.height,Fn.width,je]),Bc=m.useMemo(()=>Om(Tt,je),[Tt,je]),Kc=m.useCallback(()=>{b==="notebook"&&Vm(()=>Ut.current)},[Ut,b]),Fe=m.useCallback(()=>{if(pa(),jr.current?.({status:"cancelled",message:"Pending action cancelled on screen."}),E?.kind==="chain-step"&&i){const e=E.chainId;Ot("videobook.active-chain",""),w("chain",{action:"cancel",book_id:i,chain_id:e}).catch(()=>{})}le(null),O(null),Te(null),ko()},[i,w,pa,ko,E]),Jc=m.useCallback(e=>{O(t=>t?.kind!=="routed"||t.plan.tool!=="post"&&t.plan.routedTool!=="post"?t:{...t,plan:{...t.plan,params:Gm(t.plan.params,e)}})},[]),Xc=m.useCallback(e=>{O(t=>{if(t?.kind!=="routed"||!t.xPostReview)return t;const o={...t.xPostReview,options:{...t.xPostReview.options,...e}};return{...t,xPostReview:o,plan:{...t.plan,params:pn(t.plan.params,to(o))}}})},[]),Ra=m.useCallback(e=>{O(t=>{if(t?.kind!=="routed"||!t.xPostReview)return t;const o=Um(t.xPostReview,e);return o===t.xPostReview?t:{...t,xPostReview:o,plan:{...t.plan,params:pn(t.plan.params,to(o))}}})},[]),Qc=m.useCallback((e,t)=>{O(o=>{if(o?.kind!=="routed"||!o.xPostReview)return o;const n={...o.xPostReview,promptOverrides:{...o.xPostReview.promptOverrides,[e]:t}};return{...o,xPostReview:n,plan:{...o.plan,params:pn(o.plan.params,to(n))}}})},[]),Yc=m.useCallback(e=>{O(t=>{if(t?.kind!=="routed"||!t.xPostReview)return t;const o={...t.xPostReview,creditsOverride:e};return{...t,xPostReview:o,plan:{...t.plan,params:pn(t.plan.params,to(o))}}})},[]),Zc=m.useCallback(e=>{O(t=>{if(t?.kind!=="split")return t;const o=t.expectations[0]?.address??"video",n={...t.command,cutPointsSeconds:e.cutPointsSeconds,outputMode:e.outputMode,selectedChunkIndexes:[e.selectedIndex]};return{...t,command:n,summary:Ji({cutPointsSeconds:n.cutPointsSeconds,outputMode:n.outputMode,selectedChunkIndexes:n.selectedChunkIndexes,sourceAddress:o,sourceDurationSeconds:t.sourceDurationSeconds})}})},[]),Xr=m.useCallback(async(e,t,o)=>{if(!i)throw new Error("Open a book before previewing generation.");return await w("preview_notebook_generation",{book_id:i,notebook_id:t.id,cell_id:e.cell.id,draft:{type:e.cell.type,...e.cell.label===void 0?{}:{label:e.cell.label},slot:e.cell.slot,prompt:Wm(e,t),provider:e.cell.provider??e.action.provider,model:e.cell.model??e.action.model,operation:e.cell.operation??e.action.operation,tool:e.cell.tool??e.action.tool,inputs:e.cell.inputs??{}},connections:e.connections.map(n=>({source_cell_id:n.sourceCellId,target_input:n.targetInput}))},{chat:o,background:!0})},[i,w]),vo=m.useRef(0);m.useEffect(()=>()=>{vo.current+=1},[i,c?.id]);const jt=m.useCallback((e,t,o)=>{const n=++vo.current,r=JSON.stringify({id:e.cell.id,prompt:e.cell.prompt,action:e.action.id,inputs:e.cell.inputs,connections:e.connections});M(o,()=>O(s=>s?.kind==="generation"&&s.draft.cell.id===e.cell.id?{...s,previewError:null,previewLoading:!0,previewStale:!0}:s)),Xr(e,t,o).then(s=>{vo.current===n&&M(o,()=>O(a=>a?.kind!=="generation"?a:JSON.stringify({id:a.draft.cell.id,prompt:a.draft.cell.prompt,action:a.draft.action.id,inputs:a.draft.cell.inputs,connections:a.draft.connections})===r?{...a,preview:s,previewError:null,previewLoading:!1,previewStale:!1}:a))}).catch(s=>{vo.current===n&&M(o,()=>O(a=>a?.kind!=="generation"?a:JSON.stringify({id:a.draft.cell.id,prompt:a.draft.cell.prompt,action:a.draft.action.id,inputs:a.draft.cell.inputs,connections:a.draft.connections})===r?{...a,previewError:s instanceof Error?s.message:String(s),previewLoading:!1,previewStale:!1}:a))})},[Xr]),$t=zm(jt,`${i}:${c?.id}:${U?.cell.id}`),yt=m.useCallback((e,t)=>{vo.current+=1,$t.cancel(),O(o=>o?.kind==="generation"&&o.draft.cell.id===e.cell.id?{...o,draft:e,previewError:null,previewLoading:!1,previewStale:!0}:o),c&&(t?jt(e,c):$t.schedule(e,c))},[c,$t,jt]),Pa=m.useCallback(e=>{U&&yt(tr(U,e),!1)},[U,yt]),ed=Hm({call:g.state==="ready"?w:void 0,bookId:i??"",surface:U?Bm(U.cell.type):null,prompt:U?.cell.prompt??"",onApply:Pa}),td=m.useCallback(e=>{if(!U)return;const t=Wo.find(o=>o.id===e);t&&yt(Xi(U,t,bt),!0)},[Wo,bt,U,yt]),od=m.useCallback(e=>{U&&yt(Km(U,e,bt),!0)},[bt,U,yt]),nd=m.useCallback((e,t)=>{U&&yt(xs(U,e,t),!0)},[U,yt]),rd=m.useCallback(()=>{!U||!c||($t.cancel(),jt(U,c))},[c,U,$t,jt]),sd=m.useCallback(e=>{Z(e),ro("selection")&&me(!0)},[Z]),Dn=m.useCallback(e=>{if(!U||!c)return;let t;try{t=Jm({actions:Qe,draft:U,document:c,sourceCellIds:e})}catch(r){h(r instanceof Error?r.message:String(r),"error");return}const o=[...t.sourceCellIds.flatMap(r=>{const s=c.cells.find(a=>a.id===r);return s?[{address:W(s.slot),cellId:s.id}]:[]}),{address:W(t.cell.slot),cellId:null}],n=t.sourceAddresses.length>0?` from ${t.sourceAddresses.join(", ")}`:"";O(r=>r?.kind==="generation"&&r.draft.cell.id===t.cell.id?{...r,draft:t,expectations:o,previewError:null,previewLoading:!1,previewStale:!0,summary:`Generate ${Gs(t.cell.type)} as ${W(t.cell.slot)}${n}`}:r),$t.cancel(),jt(t,c)},[Qe,c,U,$t,jt,h]),ad=m.useCallback(e=>{U&&Dn([...U.sourceCellIds,e])},[U,Dn]),id=m.useCallback(e=>{U&&Dn(U.sourceCellIds.filter(t=>t!==e))},[U,Dn]),Qr=m.useMemo(()=>{const e=Ho.target??Ho.sources[0]??null;return e?jl(e)?.row??null:null},[Ho]);m.useEffect(()=>{b!=="notebook"||Qr===null||Xm(()=>Ut.current,{row:Qr,zoom:je},{reducedMotion:typeof window<"u"&&typeof window.matchMedia=="function"&&window.matchMedia("(prefers-reduced-motion: reduce)").matches})},[Ut,je,Qr,b]);const ce=m.useMemo(()=>Mt.find(e=>e.id===Me)??null,[Mt,Me]),$=m.useMemo(()=>c?.cells.find(e=>e.id===Me)??null,[c,Me]),It=m.useMemo(()=>(c?.cells??[]).filter(e=>xn.has(e.id)).sort((e,t)=>e.slot.row-t.slot.row||e.slot.column-t.slot.column),[c,xn]),nn=m.useMemo(()=>new Map((c?.cells??[]).flatMap(e=>{const t=Qm(re,e.outputArtifactId);return t?[[e.id,t]]:[]})),[re,c]),ld=m.useMemo(()=>new Set([...nn].flatMap(([e,t])=>t.type==="video"||t.type==="final"?[e]:[])),[nn]),Ma=m.useMemo(()=>new Set([...nn].flatMap(([e,t])=>t.type==="image"?[e]:[])),[nn]),Ta=c&&$?Ym(c,$.id).error??ao[$.id]??null:null,ja=m.useMemo(()=>Ve.map(zi),[Ve]),Yr=$?Zm({cell:$,cells:c?.cells??[],edges:c?.edges??[],queuedCellIds:An,runErrors:ao,error:Ta,jobs:ja}):null,cd=m.useMemo(()=>!$||$.type!=="audio"&&$.type!=="image"&&$.type!=="video"&&$.type!=="analysis"?[]:ep($.inputs,$.outputArtifactId).flatMap(e=>{const t=re.get(e);return t?[t]:[]}),[re,$]),dd=m.useMemo(()=>{if(!c||!$)return null;try{const e=St(c,$.id),t=dr(c,e),o=t?re.get(t):void 0,n=o?.duration??ie(e.inputs?.durationSeconds);return!o?.mediaUrl||!n||n<1?null:{source:e,asset:o,duration:n}}catch{return null}},[re,c,$]),$a=m.useMemo(()=>{if(!c||E?.kind!=="split")return null;try{const e=St(c,E.command.sourceReference),t=dr(c,e),o=t?re.get(t):void 0,n=o?.duration??ie(e.inputs?.durationSeconds);if(!o?.mediaUrl||!n||n<1)return null;const r=gn.maximumRowCount*gn.columnCount;return{availableEmptyCells:Math.max(0,r-c.cells.length),cutPointsSeconds:E.command.cutPointsSeconds,mediaUrl:o.mediaUrl,outputMode:E.command.outputMode??"all",selectedIndex:E.command.selectedChunkIndexes?.[0]??0,sourceDurationSeconds:n,sourceFps:o.fps,sourceLabel:W(e.slot)}}catch{return null}},[re,c,E]),ud=$?xr[$.id]:void 0,fd=m.useCallback(async(e,t)=>{if(!i||!c)throw new Error("Notebook is not ready");return await w("preview_notebook_generation",{book_id:i,notebook_id:c.id,cell_id:e,draft:t},{background:!0})},[i,w,c]),md=m.useCallback(async e=>{if(!i)throw new Error("Book is not ready");const o=await w("inspect_generation_request",{book_id:i,asset_id:e},{background:!0});if(o.payload==null)throw new Error("No generation payload recorded for this attempt");return o.payload},[i,w]),pd=m.useCallback(async e=>{if(!i)throw new Error("Book is not ready");const t=await w("inspect_generation_request",{book_id:i,asset_id:e},{background:!0});return tp(t)},[i,w]),gd=m.useCallback(async e=>{if(!i)throw new Error("Book is not ready");op(await np(w,i,e))},[i,w]),rn=m.useCallback((e,t)=>{kc(o=>({...o,[e]:{...o[e]??Qi,...t}}))},[]),kd=m.useCallback(async e=>{const t=Date.now()+ow;for(;Date.now()<t;){await rt(tw);const o=Q.current;if(o.bookId!==e.bookId||o.notebookId!==e.notebookId)return{kind:"continue"};const n=performance.now(),[r,s,a]=await Promise.all([Pe.current("get_notebook",{book_id:e.bookId,notebook_id:e.notebookId},{background:!0}),Pe.current("list_assets",{book_id:e.bookId,sort:"newest",limit:200,include_referenced:!0},{background:!0}),Pe.current("list_jobs",{book_id:e.bookId,limit:200},{background:!0})]),l=ge(r),u=Lt(s),d=oo(a);l&&n>=ye.current&&(ye.current=n,Je(S=>Nt(S,u)?S:u),ct(d),Ie(l,u,d));const p=u.find(S=>S.artifactId===e.artifactId),v=rp({insight:e.insight,artifactId:e.artifactId,since:e.since,hasInsight:zl(p,e.insight),hadInsight:e.hadInsight,jobs:d});if(v.kind!=="continue")return v}return{kind:"failed",message:e.insight==="transcript"?"Transcription did not finish in time. Check the jobs screen.":"Video analysis did not finish in time. Check the jobs screen."}},[ct,Ie]),bd=m.useCallback(async(e,t)=>{if(!i)throw new Error("Book is not ready");const o=await w("read_transcript",{book_id:i,asset_id:e,raw:!0,source:t},{background:!0}),n=D(o),r=typeof n?.text=="string"?n.text:null,s=_(n?.file);if(!r||!s)throw new Error("No transcript sidecar for this asset");return{text:r,file:s}},[i,w]),wd=m.useCallback(e=>{i&&w("export_transcript_srt",{book_id:i,asset_id:e}).then(t=>{const o=D(t),n=_(o?.path);h(n?`Saved ${n}`:"Saved SRT to Downloads")}).catch(t=>{h(t instanceof Error?t.message:String(t),"error")})},[i,w,h]),$e=m.useCallback(async(e,t,o)=>{const n=await w("get_notebook",{book_id:e,notebook_id:t},{background:!0,chat:o}),r=ge(n);if(!r)throw new Error("The server returned an invalid notebook");if(o&&!o.isInScope())throw new Error("Workspace changed while refreshing the notebook.");return Ie(r,H,Ve,e),r},[Ie,H,w,Ve]),F=m.useCallback(async(e,t,o,n)=>{if(o?.()===!1||n&&!n.isInScope())return;const r=Lr.current+1;Lr.current=r;const s=await Yi(async()=>await Promise.all([w("list_notebooks",{book_id:e},{background:!0,chat:n}),w("list_assets",{book_id:e,sort:"newest",limit:200,include_referenced:!0},{background:!0,chat:n}),w("get_primary_sequence",{book_id:e},{background:!0,chat:n}),w("list_jobs",{book_id:e,limit:200},{background:!0,chat:n}),w("list_notebook_actions",{book_id:e},{background:!0,chat:n})]),()=>Lr.current===r&&o?.()!==!1&&(!n||n.isInScope()));if(s.kind==="stale")return;if(s.kind==="error")throw s.error;const[a,l,u,d,p]=s.value,v=Zi(a),S=Lt(l),A=oo(d),y=yn(`videobook.active-notebook:${e}`),R=v.find(q=>q.id===t)??v.find(q=>q.id===y)??v[0]??null;if(K(e),Ot("videobook.active-book",e),Je(S),Ee(Ke(u)),Ws(A),Js(sp(p)),zs(Date.now()),!R){xe(null),ht([]),$n([]);return}return Ot(`videobook.active-notebook:${e}`,R.id),Ie(R,S,A,e),Ln(e,R,S),R.cells.some(q=>q.type==="goal")&&va({bookId:e,notebookId:R.id}).catch(()=>{}),R},[Ie,w,va,Ln]),Zr=e=>{tt("notebook"),Yt(e),io(e)},hd=async(e="",t)=>{if(!i||!c)return{ok:!1,message:"Open a notebook first."};if(!e)return mo?(Zr(mo.cellId),{ok:!0,message:`Opened goal ${mo.address??""}`.trim()}):{ok:!1,message:"Mention the reference images or videos, for example /goal @a1 @a2 as a short clip."};if(sb(e).length===0)return{ok:!1,message:"Mention the reference images or videos, for example /goal @a1 @a2 as a short clip"};const o={bookId:i,notebookId:c.id},n=await ya(o,{action:"create",brief:e,request_id:xt()},t);return Q.current.bookId!==o.bookId||Q.current.notebookId!==o.notebookId||t?.isCurrent()===!1?{ok:!0,message:"Goal saved in its notebook."}:(await F(o.bookId,o.notebookId,void 0,t),io(n.cellId),ae(t),Zr(n.cellId),{ok:!0,message:`Planning your video goal in ${n.address??"a new tile"}`})},vd=async e=>{if(!Bo)throw new Error("Open the goal notebook first.");const t=Bo,o=await ya(t,e);return e.action==="combine"?(await F(t.bookId,t.notebookId),o):(e.action!=="approve"&&e.action!=="regenerate"&&e.action!=="revise"&&e.action!=="retry"||(Q.current.bookId===t.bookId&&Q.current.notebookId===t.notebookId&&ae(),await F(t.bookId,t.notebookId)),o)},yd=async e=>{if(!Bo)return;const t=Bo,n=(await F(t.bookId,t.notebookId,()=>Q.current.bookId===t.bookId&&Q.current.notebookId===t.notebookId))?.cells.find(r=>r.type==="timeline");if(!n)throw new Error("Add a timeline cell to preview the assembled sequence.");bs(n.id,e)},dt=m.useCallback((e,t,o=!1)=>{No(n=>n?.key===e?{...n,subjectMap:t,subjectMapLoading:o}:n)},[]),On=m.useCallback(async(e,t,o)=>{const n=await ap({initialMap:o,read:async()=>Fs(e,await w("get_image_subject_map",{book_id:e.bookId,artifact_id:e.asset.artifactId,object_hash:e.asset.objectHash},{background:!0})),publish:r=>dt(e.key,r),isCurrent:()=>We.current===t});n.kind==="stale"||n.kind==="terminal"||We.current!==t||dt(e.key,Ds(e,n.kind==="timeout"?new Error("Subject analysis did not finish within 27 minutes. Retry to check or restart it."):n.error,n.map))},[w,dt]),Vn=m.useCallback((e,t,o,n="view")=>{if(!i||!c)return;const r={mode:n,initialInstruction:sa.current.get(i)??yn(`videobook.image-edit-instruction:${i}`),key:[i,c.id,e.id,t.artifactId,t.objectHash].join(":"),bookId:i,notebookId:c.id,cellId:e.id,address:Se(e.slot),asset:t,returnFocus:o??(document.activeElement instanceof HTMLElement?document.activeElement:null),subjectMap:null,subjectMapLoading:t.type==="image"&&!!t.objectHash};ip(document.querySelector(".command-composer")),at.current+=1,gt(null),Vt(null);const s=We.current+1;We.current=s,Ar(null),_r(!1),No(r),me(!0),t.type==="image"&&Jo.ensureLoaded(i),!(t.type!=="image"||!t.objectHash)&&w("get_image_subject_map",{book_id:i,artifact_id:t.artifactId,object_hash:t.objectHash},{background:!0}).then(a=>{if(We.current!==s)return;const l=Fs(r,a);dt(r.key,l),l.status==="analyzing"&&On(r,s,l)}).catch(a=>{We.current===s&&dt(r.key,Ds(r,a))})},[i,w,Jo,c,dt,On]),Kt=m.useCallback(()=>{at.current+=1,gt(null),Vt(null),We.current+=1,Ar(null),_r(!1),No(null)},[]),Id=async(e,t)=>{const o=D(await w("extract_notebook_frame",{book_id:e.bookId,notebook_id:e.notebookId,source_cell_id:e.cellId,frame_mode:"time",timestamp_seconds:Math.round(t*1e3)/1e3})),n=_(o?.cell_id),r=_(o?.address),s=_(o?.run_id),a=_(o?.job_id);if(!n||!r||!s||!a)throw new Error("The server did not return the frame extraction cell");return ae(),ne(n,null),oe(n,!0),Pt({bookId:e.bookId,notebookId:e.notebookId,cellId:n,address:r.replace(/^@/,""),runId:s,jobOperationId:a,intervalMs:wn,timeoutMs:hn,maxPollFailures:fr}).then(l=>{if(l.kind==="failed"||l.kind==="timeout"){const u=l.message??`Frame extraction into ${r} failed`;ne(n,u),h(u,"error")}}).finally(()=>{oe(n,!1)}),r},Cd=m.useCallback(async(e,t=!1)=>{if(!e.asset.objectHash)throw new Error("This image does not expose an immutable object hash");if(!ur({provider:"kie",model:"seedream/5-pro-layer-decomposition",tool:"analyze_image_subjects"}))return;const o=We.current+1;We.current=o,dt(e.key,{status:"analyzing",artifactId:e.asset.artifactId,objectHash:e.asset.objectHash,width:e.asset.width,height:e.asset.height,baseUrl:e.subjectMap?.baseUrl??null,jobId:null,startedAt:new Date().toISOString(),error:null,subjects:e.subjectMap?.subjects??[]},!0);try{const n=await w("analyze_image_subjects",{book_id:e.bookId,artifact_id:e.asset.artifactId,object_hash:e.asset.objectHash,...t?{force:!0}:{}});if(We.current!==o)return;const r=Fs(e,n);dt(e.key,r),r.status==="analyzing"&&On(e,o,r)}catch(n){throw We.current===o&&dt(e.key,Ds(e,n)),n}},[w,dt,On]),Gn=m.useCallback(async(e,t,o)=>{if(!e.asset.objectHash)throw new Error("This image does not expose an immutable object hash");if(i!==e.bookId)throw new Error("The active book changed while the image editor was open");if(Q.current.notebookId!==e.notebookId)throw new Error("The active notebook changed while the image editor was open");const n=t.model??lp,r=n.startsWith("fal-ai/")||n.startsWith("alibaba/")?"fal":"kie";if((t.operation!=="remove"||(t.editRegions?.length??0)>0)&&!ur({provider:r,model:n,tool:"edit_image_subjects"}))return!1;const s=We.current,a=()=>{const v=Q.current;return We.current===s&&v.bookId===e.bookId&&v.notebookId===e.notebookId},l=await Yi(async()=>await w("edit_image_subjects",{book_id:e.bookId,notebook_id:e.notebookId,source_cell_id:e.cellId,artifact_id:e.asset.artifactId,object_hash:e.asset.objectHash,...t.subjectIds.length>0?{subject_ids:t.subjectIds}:{},operation:t.operation,...t.model?{model:t.model}:{},...t.prompt?{prompt:t.prompt}:{},...t.editRegions?.length?{edit_regions:t.editRegions}:{},...t.regions&&t.regions.length>0?{regions:t.regions.map(v=>({replacement_artifact_id:v.replacementArtifactId,...v.box?{box:v.box}:{},...v.subjectId?{subject_id:v.subjectId}:{},...v.note?{note:v.note}:{}}))}:{}},{chat:o}),a);if(l.kind==="stale")return!1;if(l.kind==="error")throw l.error;const u=l.value,d=_(D(u)?.status)??"queued";M(o,()=>h(t.operation==="remove"?`${t.editRegions?.length?"Region":"Subject"} removal ${d}`:t.operation==="replace"?`Region replacement ${d}`:t.operation==="whole_image"?`Whole-image edit ${d}`:`${t.editRegions?.length?"Region":"Subject"} edit ${d}`)),await F(e.bookId,e.notebookId,a,o).catch(()=>{});const p=_(D(u)?.producer_cell_id);return p&&a()&&M(o,()=>{Kt(),Z(p,o),Le(null),kt(null),ae(o),io(p)}),!0},[i,w,Kt,ae,F,io,Z,h]),yo=m.useCallback(async()=>{const e=await w("list_books",{sort:"newest"}),t=cp(e);return j(t),t},[w]),Sd=m.useCallback(async(e,t=!1)=>{const o=`@${e.id}`;if(e.owningBookId!==i)return h(`Open ${e.owningBookName} to forget ${o}`,"error"),{ok:!1,message:`Open ${e.owningBookName} first`};if(!t&&!window.confirm(dp(o)))return{ok:!1,message:"Forget cancelled"};T(!0);try{let n=el(await w("delete_asset",{book_id:i,asset_id:e.artifactId,forget:!0}));if(n.status==="in_use"){if(!window.confirm(Es(o,n.references)))return{ok:!1,message:"Forget cancelled; media is still in use"};n=el(await w("delete_asset",{book_id:i,asset_id:e.artifactId,forget:!0,clear_references:!0}))}return n.status==="in_use"?(h(Es(o,n.references).split(`
|
|
9
9
|
`)[0],"error"),{ok:!1,message:Es(o,n.references).split(`
|
|
10
|
-
`)[0]}):(h(tl(o,n)),await F(i,c?.id),await
|
|
10
|
+
`)[0]}):(h(tl(o,n)),await F(i,c?.id),await yo(),{ok:!0,message:tl(o,n)})}catch(n){return h(n instanceof Error?n.message:String(n),"error"),{ok:!1,message:n instanceof Error?n.message:String(n)}}finally{T(!1)}},[i,w,c?.id,F,yo,h]),Io=m.useCallback(async()=>{const[e,t]=await Promise.all([w("slash_commands",{detail:"full"}),w("list_workspace_actions",{detail:"full"})]),o=As(t);kr(o.actions),oc(or(o.actions,up(e)))},[w]),Un=(e,t,o,n)=>{if(!i)return;const r=++To.current,s=cl({bookId:i,assetId:e,languageCode:t,diarize:o,tagAudioEvents:n});w("estimate_cost",{calls:[{tool_name:"transcribe",input:s}]},{background:!0}).then(a=>{if(r!==To.current)return;const l=Hp(D(D(a)?.estimate));O(u=>u?.kind==="transcribe"&&u.assetId===e?{...u,estimateUsd:l.usd,estimateLoading:!1,estimateUnavailable:l.unavailable}:u)}).catch(()=>{r===To.current&&O(a=>a?.kind==="transcribe"&&a.assetId===e?{...a,estimateUsd:null,estimateLoading:!1,estimateUnavailable:!0}:a)})},sn=e=>{if(!i)return{ok:!1,message:"Load or create a book first."};const t=new Map(se.map(v=>[v.artifactId,v.cellAddress])),o=Y?.asset,n=Ne?.media,r=o&&wl(o.type)?{assetId:o.artifactId,type:o.type}:n&&wl(n.type)?{assetId:n.assetId,type:n.type}:null,s=Ug({assetRef:e.assetRef,selectedCell:$?{outputArtifactId:$.outputArtifactId,type:$.type}:null,preview:r,assets:H,addressByArtifactId:t});if(!s.ok)return s;const a=e.languageCode?.trim()??"",l=e.diarize??!0,u=e.tagAudioEvents??!0;at.current+=1,L(e.chat,!1,()=>le(null)),L(e.chat,!1,()=>Te(null)),L(e.chat,!1,()=>Xe(null)),L(e.chat,!1,()=>gt(null)),L(e.chat,!0,()=>O({kind:"transcribe",assetId:s.assetId,languageCode:a,diarize:l,tagAudioEvents:u,estimateUsd:null,estimateLoading:s.assetId!==null,estimateUnavailable:!1})),me(!0),s.assetId?Un(s.assetId,a,l,u):To.current+=1;const d=s.assetId?t.get(s.assetId):null,p=d?`@${d}`:s.assetId?H.find(v=>v.artifactId===s.assetId)?.label??s.assetId:null;return Bl(p?`Transcribe review ready for ${p}`:"Transcribe review ready. Choose a clip.")},xd=e=>{const t=sn({assetRef:e});t.ok||h(t.message,"error")},Ce=async(e,t,o,n,r)=>{if(e==="tool.transcribe"){const d=sn({assetRef:_(t?.asset_id)??void 0,languageCode:_(t?.language_code)??"",diarize:typeof t?.diarize=="boolean"?t.diarize:!0,tagAudioEvents:typeof t?.tag_audio_events=="boolean"?t.tag_audio_events:!0,chat:r});d.ok||M(r,()=>h(d.message,"error"));return}if(g.state!=="ready")return;me(!0);const s=document.activeElement instanceof HTMLElement?document.activeElement:null,a=n??qe?.opener??(s===document.body||s?.closest(".command-composer")?document.querySelector('[aria-label="Videobook command input"]'):s),l=typeof t?.book_id=="string"?t.book_id:i,u=++at.current;if(e)gt(null),Xe({key:u,actionId:e,values:t,query:o,opener:a});else{const d=l===i&&Y?.asset.type==="image"?`image-edit:${Y.key}`:`chat:${l}`;Xe(null),gt({key:u,query:o??"",values:t,bookId:l,session:d}),Vt({bookId:l,session:d,opener:a})}wr({loading:!0,error:null});try{const d=e&&Et.length?{actions:Et}:As(await w("list_workspace_actions",{detail:"full"},{chat:r}));if(u!==at.current||r&&!r.isCurrent())return;kr(d.actions);const p=d.actions.find(v=>v.id===e);if(p){const v=t?.asset_id??t?.artifact_id,S={...ag(p,{...fn,assetId:typeof v=="string"?v:fn.assetId}),...t};p.handler.kind==="tool"&&p.handler.tool==="create_notebook_cell"&&t?.slot&&(S.cell={...D(S.cell),slot:t.slot});const A=await ig(p,S,(q,V)=>w(q,{book_id:S.book_id??i,...V},{chat:r}));if(u!==at.current||r&&!r.isCurrent())return;const R=p.handler.kind==="tool"&&["list_notebooks","list_entities","list_book_actions","search_archive"].includes(p.handler.tool)&&p.handler.kind==="tool"?{message:`${p.title} loaded`,value:await w(p.handler.tool,S,{chat:r})}:void 0;if(u!==at.current||r&&!r.isCurrent())return;Xe(q=>q?.key===u?{...q,values:{...S,...A.values},resources:A,result:R}:q)}wr({loading:!1,error:null})}catch(d){if(u!==at.current||r&&!r.isCurrent())return;wr({loading:!1,error:d instanceof Error?d.message:String(d)})}},qa=()=>{at.current+=1;const e=Cn?.opener;gt(null),Vt(null),Ui(()=>e?.isConnected?e:null)},Wn=m.useCallback(async()=>{const e=fp(await w("list_chat_models",{})),t=yn("videobook.chat-model");ic(e),Ks(o=>{const n=Is(e,t||o);return Ot("videobook.chat-model",n),n})},[w]),Ed=m.useCallback(async()=>{await Promise.all([Io(),Wn()])},[Io,Wn]),Ad=m.useCallback(e=>{const t=Is(vr,e);Ks(t),Ot("videobook.chat-model",t)},[vr]),Co=m.useCallback(async()=>{try{return await Io(),null}catch(e){return e instanceof Error?e.message:String(e)}},[Io]),_d=m.useCallback(async e=>{T(!0);try{const[t]=await Promise.all([yo(),Io(),Wn()]),o=mp(t,e??i);o?(await F(o.bookId),h(`Loaded ${o.name}`)):(K(""),xe(null),Je([]),Js([]),Ee(null),ht([]),$n([]),h("No videobook projects are available."))}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{T(!1)}},[i,Io,F,yo,Wn,h]),So=m.useCallback(async()=>{const e=Vo.current+1;Vo.current=e,Pr(!0),Mr(!0),Tr(null);try{return await yo(),{ok:!0}}catch(t){const o=vn(t);return Vo.current===e&&Tr(o.error),h(o.error,"error"),o}finally{Vo.current===e&&Mr(!1)}},[yo,h]),Jt=m.useCallback(e=>{if(e){So();return}Vo.current+=1,Pr(!1),Mr(!1),Tr(null)},[So]),Rd=m.useCallback(()=>{So()},[So]),tt=m.useCallback(e=>{I(e);const t=pp(e);window.location.pathname!==t&&window.history.pushState({},"",t)},[]);m.useEffect(()=>{document.title=gp(b)},[b]),m.useEffect(()=>{const e=()=>{const t=Ni(window.location.pathname);I(t)};return window.addEventListener("popstate",e),()=>window.removeEventListener("popstate",e)},[]);const Na=m.useCallback(async e=>{T(!0);try{await F(e);const t=x.find(o=>o.bookId===e);return h(t?`Opened ${t.name}`:"Book opened"),tt("notebook"),Jt(!1),{ok:!0}}catch(t){const o=vn(t);return h(o.error,"error"),o}finally{T(!1)}},[x,Jt,F,h,tt]),La=m.useCallback(async e=>{T(!0);try{const t=ol(await w("create_book",{name:e}));if(!t)throw new Error("The server returned an invalid project");j(n=>[t,...n.filter(r=>r.bookId!==t.bookId)]),await F(t.bookId);const o=await Co();return tt("notebook"),Jt(!1),h(o?`Created ${t.name}; commands could not refresh: ${o}`:`Created ${t.name}`),{ok:!0}}catch(t){const o=vn(t);return h(o.error,"error"),o}finally{T(!1)}},[w,Jt,Co,F,h,tt]),Fa=m.useCallback(async(e,t)=>{T(!0);try{const o=ol(await w("rename_book",{book_id:e,name:t}));if(!o)throw new Error("The server returned an invalid project");j(r=>r.map(s=>s.bookId===e?o:s));const n=await Co();return h(n?`Renamed to ${o.name}; commands could not refresh: ${n}`:`Renamed to ${o.name}`),{ok:!0}}catch(o){const n=vn(o);return h(n.error,"error"),n}finally{T(!1)}},[w,Co,h]),Da=m.useCallback(async(e,t)=>{if(x.length<2)return{ok:!1,error:"Create another project before deleting this one"};const o=x.find(r=>r.bookId===e),n=x.find(r=>r.bookId!==e);if(!o||!n)return{ok:!1,error:"The selected project is no longer available"};T(!0);try{await w("delete_book",{book_id:e,confirm_name:t}),j(s=>s.filter(a=>a.bookId!==e)),e===i&&(await F(n.bookId),tt("notebook"),Jt(!1));const r=await Co();return h(r?`Deleted ${o.name}; commands could not refresh: ${r}`:`Deleted ${o.name}`),{ok:!0}}catch(r){const s=vn(r);return h(s.error,"error"),s}finally{T(!1)}},[i,x,w,Jt,Co,F,h,tt]),an=c?.posts?.find(e=>e.id===Me),Oa=async e=>{if(!(!i||!c||g.state!=="ready")){T(!0);try{const t=await w("create_post",{book_id:i,notebook_id:c.id,...e?{source_cell_id:e}:{}});await F(i,c.id),Yt(t.id),h(`Created Post ${t.address}`)}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{T(!1)}}},es=async(e,t)=>{if(!i||!c)return;if(e==="post"){const r=c.cells.find(s=>s.id===Me&&s.type!=="post"&&s.outputArtifactId&&["image","video","generate_image","generate_video","concat","splice","split_video"].includes(s.type));await Oa(r?.id);return}const o=e==="timeline"?c.cells.find(r=>r.type==="timeline"):null;if(o){Z(o.id),me(!0),document.querySelector(`[data-id="${o.id}"]`)?.scrollIntoView({block:"nearest",inline:"nearest"});return}let n;try{n=t?fl(t,Jr):Mo(e,c.cells,Ge),e==="timeline"&&(n={row:n.row,column:0});const r=new Set(Tl({type:e,slot:n}).map(ml));if(vt.some(s=>r.has(ml(s)))){h(e==="timeline"?"Choose a completely empty row for Timeline":"Choose an empty grid square for the new cell","error");return}}catch(r){h(r instanceof Error?r.message:String(r),"error");return}T(!0);try{const r=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:{type:e,slot:n,...e==="prompt"||e==="analyze"||no(e)?{prompt:""}:{}}})),s=await F(i,c.id);Ae(n),e==="timeline"&&typeof r?.id=="string"&&(Z(r.id),requestAnimationFrame(()=>document.querySelector(`[data-id="${r.id}"]`)?.scrollIntoView({block:"nearest",inline:"nearest"}))),Ft(e)&&typeof r?.id=="string"?Eo(r.id,s):ae(),h(`Added ${W(n)} cell`)}catch(r){h(r instanceof Error?r.message:String(r),"error")}finally{T(!1)}},Pd=async e=>{if(!i||!c||!ce)return!1;T(!0);try{return await w("update_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:ce.id,cell:e}),await $e(i,c.id),Ae(ce.data.slot),h("Cell saved"),!0}catch(t){return h(t instanceof Error?t.message:String(t),"error"),!1}finally{T(!1)}},Md=async(e,t)=>{if(!i||!c||!$)return;const o=c.edges.some(n=>n.target===$.id&&n.targetInput===e);T(!0);try{await w("set_notebook_cell_input",{book_id:i,notebook_id:c.id,target_cell_id:$.id,target_input:e,source_cell_id:t}),await $e(i,c.id),h(t?o?"Input source replaced":"Input source attached":"Input source cleared")}catch(n){h(n instanceof Error?n.message:String(n),"error")}finally{T(!1)}},xo=async(e,t)=>{if(!i||!c||e.length===0)return;const o=[...new Map(e.map(p=>[p.id,p])).values()],n=new Set(o.map(p=>p.id)),r=o.map(p=>W(p.slot)),s=o.length,a=new Set(Mt.filter(p=>p.data.status==="error").map(p=>p.id));if((t?.confirm??o.some(p=>!a.has(p.id)))&&!window.confirm(s===1?`Delete ${r[0]}?
|
|
11
11
|
|
|
12
12
|
This removes the cell and its connections. This cannot be undone.`:`Delete ${s} selected cells?
|
|
13
13
|
|
|
14
14
|
${r.join(", ")}
|
|
15
15
|
|
|
16
|
-
This removes the cells and their connections. This cannot be undone.`))return;const u=new Set,d=()=>{const p=It.map(v=>v.id).filter(v=>!u.has(v)).at(-1)??null;bo(new Set([...lt.current].filter(v=>!u.has(v)))),qo(v=>v&&!u.has(v)?v:p),Le(v=>v&&u.has(v)?null:v)};ta(n),ht(p=>p.map(v=>n.has(v.id)?{...v,data:{...v.data,deleting:!0}}:v)),T(!0);try{await rt(180);for(const p of o)await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:p.id}),u.add(p.id);Y&&u.has(Y.cellId)&&Kt(),await F(i,c.id),d(),h(s===1?`${r[0]} deleted`:`${s} cells deleted`)}catch(p){Y&&u.has(Y.cellId)&&Kt(),await F(i,c.id).catch(()=>{}),d();const v=p instanceof Error?p.message:String(p);h(u.size>0?`Deleted ${u.size} of ${s} cells. ${v}`:v,"error")}finally{ht(p=>p.map(v=>n.has(v.id)?{...v,data:{...v.data,deleting:!1}}:v)),ta(new Set),T(!1)}},Md=async()=>{$&&await So([$])},Va=async()=>{await So(It)},Td=e=>{if(e.key!=="Backspace"&&e.key!=="Delete")return;const t=e.target;t instanceof HTMLElement&&t.closest('input, textarea, select, button, a, [contenteditable="true"]')||G||It.length===0||(e.preventDefault(),e.stopPropagation(),Va())},jd=async e=>{if(!(!i||!c))try{await w("move_notebook_cells",{book_id:i,notebook_id:c.id,slots:e.map(t=>({id:t.id,row:t.data.slot.row,column:t.data.slot.column}))}),await $e(i,c.id)}catch(t){const o=t instanceof Error?t.message:String(t);await $e(i,c.id).catch(()=>{}),h(o,"error")}},$d=async()=>{if(!(!i||!c||c.cells.length===0)){T(!0);try{const e=ge(await w("get_notebook",{book_id:i,notebook_id:c.id}));if(!e)throw new Error("Unable to read the notebook before arranging");if(Q.current.bookId!==i||Q.current.notebookId!==c.id)return;const t=tg(e);if(!t.ok)throw new Error(t.message);const o=new Map(e.cells.map(a=>[a.id,a.slot])),n=t.slots.some(a=>{const l=o.get(a.id);return l?.row!==a.row||l?.column!==a.column}),r=()=>og(()=>Ut.current);if(!n){await $e(i,c.id),h("Notebook is already auto-arranged"),r();return}await w("move_notebook_cells",{book_id:i,notebook_id:c.id,...e.revision?{expected_revision:e.revision}:{},slots:t.slots}),await $e(i,c.id);const s=Me?t.slots.find(a=>a.id===Me):void 0;s&&Ae({row:s.row,column:s.column}),h(`Auto-arranged ${t.slots.length} ${t.slots.length===1?"tile":"tiles"}`),r()}catch(e){await $e(i,c.id).catch(()=>{}),h(e instanceof Error?e.message:String(e),"error")}finally{T(!1)}}},qd=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"No notebook is open"};const n=$k(c,ld,t,e);if(!n.ok)return M(o,()=>h(n.message,"error")),{ok:!1,message:n.message};const r=e==="column"?`column ${t.column+1}`:`row ${String.fromCharCode(97+t.row)}`;if(n.movedCount===0){const a=`Videos are already arranged in ${r}`;return M(o,()=>h(a)),{ok:!0,message:a}}const s=_(D(c)?.revision);T(!0);try{await w("move_notebook_cells",{book_id:i,notebook_id:c.id,...s?{expected_revision:s}:{},slots:n.slots},{chat:o}),await $e(i,c.id,o),Ae({row:t.row,column:t.column});const a=n.slots.length-n.displacedCount,l=`Arranged ${a} ${a===1?"video":"videos"} in ${r}`;return M(o,()=>h(l)),{ok:!0,message:l}}catch(a){await $e(i,c.id,o).catch(()=>{});const l=a instanceof Error?a.message:String(a);return M(o,()=>h(l,"error")),{ok:!1,message:l}}finally{T(!1)}},Ga=async(e,t)=>{if(!i||!c)return{ok:!1,message:"No notebook is open"};const o=Zg(c,Ma,e);if(!o.ok)return M(t,()=>h(o.message,"error")),{ok:!1,message:o.message};const n=W(e);if(o.movedCount===0){const s=`Images are already grouped from ${n}`;return M(t,()=>h(s)),{ok:!0,message:s}}const r=_(D(c)?.revision);T(!0);try{await w("move_notebook_cells",{book_id:i,notebook_id:c.id,...r?{expected_revision:r}:{},slots:o.slots},{chat:t}),await $e(i,c.id,t),Ae({row:e.row,column:e.column});const s=o.slots.length-o.displacedCount,a=`Grouped ${s} ${s===1?"image":"images"} from ${n}`;return M(t,()=>h(a)),{ok:!0,message:a}}catch(s){await $e(i,c.id,t).catch(()=>{});const a=s instanceof Error?s.message:String(s);return M(t,()=>h(a,"error")),{ok:!1,message:a}}finally{T(!1)}},Nd=async e=>{if(!(!i||!c||!e.source||!e.target)){if(!ll(c.edges,e,c.cells)){const t=c.cells.find(n=>n.id===e.source),o=c.cells.find(n=>n.id===e.target);h(t&&o?`Connecting ${W(t.slot)} to ${W(o.slot)} would create a cycle`:"That connection would create a cycle","error");return}T(!0);try{await w("connect_notebook_cells",{book_id:i,notebook_id:c.id,source_cell_id:e.source,target_cell_id:e.target,target_input:pl(c,e)}),await $e(i,c.id),h("Cells connected")}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{T(!1)}}},Ld=async e=>{if(!(!i||!c||e.length===0))try{await Promise.all(e.map(t=>w("disconnect_notebook_cells",{book_id:i,notebook_id:c.id,edge_id:t}))),await $e(i,c.id),h("Connection removed")}catch(t){h(t instanceof Error?t.message:String(t),"error")}},Ua=async(e,t)=>{if(!i)throw new Error("Choose a book before uploading media");const o=await Xl(e),n=D(await w("check_duplicate_bytes",{book_id:i,object_hash:o})),s=(Array.isArray(n?.matches)?n.matches:[]).map(p=>D(p)).find(p=>{const v=p&&_(p.kind);return v!==null&&Vs(t,v)}),a=s&&_(s.artifact_id);if(a)return{artifactRef:a,reusedExisting:!0};const l=await fetch(`/api/books/${encodeURIComponent(i)}/upload?filename=${encodeURIComponent(e.name)}`,{method:"POST",body:e}),u=D(await l.json());if(!l.ok)throw new Error(_(u?.error)??`Upload failed: ${e.name}`);const d=_(u?.assetId);if(!d)throw new Error("Upload did not return an asset id");return{artifactRef:d,reusedExisting:!1}},Wa=async(e,t)=>{if(!i||!c||g.state!=="ready")return;const o=nr(),n=c.cells.find(a=>a.id===e),r=n&&Ft(n.type);if(!n||!r)return;if(n.outputArtifactId||c.edges.some(a=>a.target===e)){Zo(e,"This media slot already contains media.");return}if(Rs(t)!==r){Zo(e,`Choose one ${r} file for this slot.`);return}Rt(e,"upload");try{const{artifactRef:a,reusedExisting:l}=await Ua(t,r);await w("set_notebook_media_slot",{book_id:i,notebook_id:c.id,cell_id:e,artifact_ref:a}),await F(i,c.id),Rt(e,null),h(l?`Reused @${a} in media slot`:`Uploaded and attached @${a}`),Nn({bookId:i,notebookId:c.id,cellId:e,address:Se(n.slot),artifactId:a})}catch(a){const l=a instanceof Error?a.message:String(a);Zo(e,l),h(l,"error")}finally{o()}},ts=async(e,t)=>{if(!i||!c)return;const o=nr();if(G){h("Wait for the current operation to finish","error");return}const n=Rs(t);if(!n){h("Drop an image, video, or audio file on an open square","error");return}if(vt.some(l=>l.row===e.row&&l.column===e.column)){h("Choose an empty grid square for the media file","error");return}const r=W(e);let s=null,a=!1;T(!0);try{const{artifactRef:l,reusedExisting:u}=await Ua(t,n),d=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:{type:n,slot:e}}));if(s=d&&_(d.id),!s)throw new Error("The server did not return the new media cell");await w("set_notebook_media_slot",{book_id:i,notebook_id:c.id,cell_id:s,artifact_ref:l}),a=!0,z?.cellId===null&&zn(),ae(),Ae(e),await F(i,c.id),h(u?`Reused @${l} at ${r}`:`Uploaded and attached @${l} at ${r}`),Nn({bookId:i,notebookId:c.id,cellId:s,address:Se(e),artifactId:l})}catch(l){let u=l instanceof Error?l.message:String(l);if(s&&!a)try{await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:s})}catch(d){const p=d instanceof Error?d.message:String(d);u=`${u}. The empty ${r} cell could not be removed: ${p}`}await F(i,c.id).catch(()=>{}),h(u,"error")}finally{T(!1),o()}},zn=()=>{const e=$g(Fr.current);_e.current+=1,fe.lifecycle.close(),ke(null),Fr.current=null,e()},Ct=async(e,t,o,n,r,s,a)=>{const l=c?.cells.find(S=>S.id===e),u=a??(e===null?"all":l&&Ft(l.type));if(!u)return;const d=r??(z?.cellId===e?Bb(fe.state):{mode:"text",reference:null,referenceStartSeconds:"0",referenceDurationSeconds:""}),p=s??(z?.cellId===e?z.tagFilters:[]),v=_e.current+1;_e.current=v,ke(S=>!S||S.cellId!==e?S:{...S,query:t,tagFilters:[...p],assets:n?S.assets:[],page:n?S.page:mr,booksWithErrors:n?S.booksWithErrors:[],preparingIndex:!1,loading:!n,loadingMore:n,error:null});try{let S;try{S=d.mode==="video-reverse"&&d.reference?Pg(d.referenceStartSeconds,d.referenceDurationSeconds,d.reference):void 0}catch(q){const V=fe.lifecycle.getState().reference===d.reference?fe.lifecycle.resetInvalidRange(q):q instanceof Error?q.message:String(q);throw new Error(V)}const A=()=>_e.current!==v,y=await Mg({search:()=>w("search_library_assets",{...d.mode==="text"&&t.trim()?{query:t.trim()}:{},...d.mode!=="text"&&d.reference?{reference_id:d.reference.referenceId}:{},...S?{reference_range:S}:{},kinds:u==="all"?["audio","image","video"]:[u],...Tg(p),limit:mr.limit,offset:o}),listJobs:(q,V)=>w("list_jobs",{book_id:q,job_ids:V},{background:!0}),onPreparing:q=>{A()||ke(V=>V&&V.cellId===e?{...V,preparingIndex:q}:V)},isCancelled:A});if(A())return;const R=jg(y);ke(q=>{if(!q||q.cellId!==e)return q;const V=R.assets.filter(N=>Vs(u,N.type)),X=n?[...q.assets,...V]:V,P=new Map(X.map(N=>[`${N.owningBookId}:${N.artifactId}`,N]));return{...q,assets:[...P.values()],page:R.page,booksWithErrors:R.booksWithErrors,unindexedVisualAssets:R.unindexedVisualAssets,loading:!1,loadingMore:!1}})}catch(S){if(_e.current!==v)return;const A=S instanceof Error?S.message:String(S);ke(y=>y&&y.cellId===e?{...y,loading:!1,loadingMore:!1,error:A}:y),h(A,"error")}},za=(e,t=c)=>{const o=t?.cells.find(r=>r.id===e),n=o?Ft(o.type):null;return!o||!n||o.outputArtifactId||t?.edges.some(r=>r.target===e)?null:n},xo=(e,t=c,o)=>{if(!t||g.state!=="ready")return;const n=e===null?"all":za(e,t);n&&((e===null||lt.current.size!==1||!lt.current.has(e))&&Z(e),Le(null),kt(null),me(!0),Fr.current=document.activeElement instanceof HTMLElement?document.activeElement:null,fe.lifecycle.close(),e&&Rt(e,null),ke({unindexedVisualAssets:0,preparingIndex:!1,bookId:i,notebookId:t.id,cellId:e,slot:o,query:"",draftQuery:"",assets:[],page:mr,booksWithErrors:[],loading:!0,loadingMore:!1,error:null,activeArtifactId:null,tagFilters:[],tagSuggestions:[]}),Ct(e,"",0,!1,{mode:"text",reference:null,referenceStartSeconds:"0",referenceDurationSeconds:""},[],n))},Fd=()=>{zn(),me(!1)},os=e=>{Ao("notebook"),xo(null,c,e)},Dd=async e=>{if(!i||!c||!z||g.state!=="ready"||G)return;const t=z,o=_e.current,n=()=>_e.current===o&&Q.current.bookId===t.bookId&&Q.current.notebookId===t.notebookId;let r=t.cellId;const s=c.cells.find(d=>d.id===r),a=r===null?Os(e.type):s&&Ft(s.type);if(!a||!Vs(a,e.type))return;r&&Rt(r,"attach"),ke(d=>d===t?{...d,activeArtifactId:e.artifactId,error:null}:d);let l=null,u=!1;T(!0);try{if(r===null){const d=t.slot??Mo(a,c.cells,Ge),p=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:{type:a,slot:d}}));if(l=p&&_(p.id),!l)throw new Error("The server did not return the new media cell");r=l,Ae(d)}if(e.owningBookId===i?await w("set_notebook_media_slot",{book_id:i,notebook_id:c.id,cell_id:r,artifact_ref:e.artifactId}):await w("attach_library_asset",{source_book_id:e.owningBookId,source_artifact_id:e.artifactId,target_book_id:i,notebook_id:c.id,cell_id:r,expected_output_artifact_id:s?.outputArtifactId??null}),u=!0,!n()||(await F(i,c.id),!n()))return;Rt(r,null),h(e.owningBookId===i?`Attached @${e.id}`:`Copied and attached @${e.id} from ${e.owningBookName}`),(t.cellId!==null||lt.current.size===0)&&(zn(),l&&ae())}catch(d){let p=d instanceof Error?d.message:String(d);if(l&&!u)try{await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:l})}catch(v){p+=`. The empty cell could not be removed: ${v instanceof Error?v.message:String(v)}`}if(!n())return;t.cellId&&Zo(t.cellId,p),ke(v=>v&&v.cellId===t.cellId?{...v,activeArtifactId:null,error:p}:v),h(p,"error")}finally{!n()&&t.cellId&&Q.current.bookId===t.bookId&&Rt(t.cellId,null),T(!1)}},Bn=mp({callTool:w,ready:g.state==="ready"}),Od=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before speaking."};let n=null,r=!1;try{if(!_t)throw new Error("Offline: cloud generation is unavailable. Local search, editing, playback, and export remain available.");const s=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(!s)throw new Error("The server returned an invalid notebook");const a=await qk({bookId:i,callTool:(y,R)=>w(y,R,{chat:o}),document:s,lastWorkSlot:Ge,text:e,voiceId:t,...s.revision?{expectedRevision:s.revision}:{}});n=a;const l=jl(a.cellAddress);l&&Ae(l);const u=await ko(a.cellId,"slash",o),d=u.stages.find(y=>y.kind==="queued"&&y.jobType==="generation"&&y.tool==="run_notebook_cell"&&y.input.cell_id===a.cellId);if(d?.kind!=="queued")throw new Error("The generation plan is missing its notebook cell");const p=_(d.input.notebook_id);if(p!==s.id)throw new Error("The generation plan belongs to another notebook");if(!ur(d))throw new Error("Cloud generation cancelled before sending data");L(o,!1,()=>O(null)),L(o,!1,()=>le(null));const v=await er({start:()=>w("run_notebook_cell",{book_id:i,notebook_id:p,cell_id:a.cellId,plan:u,actor:"videobook-user"},{chat:o}),onStarting:()=>oe(a.cellId,!0),onRejected:()=>oe(a.cellId,!1)}),S=_(D(v)?.run_id),A=_(D(v)?.job_id);if(!S||!A)throw oe(a.cellId,!1),new Error("The server did not return a notebook run");return r=!0,Nk(t),ae(o),M(o,()=>h(`${a.cellAddress} queued`)),tn({bookId:i,notebookId:p,cellId:a.cellId,address:a.cellAddress.replace(/^@/,""),runId:S,jobOperationId:A},o),await F(i,c.id,void 0,o).catch(()=>{}),{ok:!0,message:`${a.cellAddress} queued`}}catch(s){const a=s instanceof Error?s.message:String(s);return n&&!r?(await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:n.cellId},{chat:o}).catch(()=>{}),await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:n.outputCellId},{chat:o}).catch(()=>{}),{ok:!1,message:a}):r?(M(o,()=>h(a,"error")),{ok:!1,message:a}):{ok:!1,message:a}}},Ba=(e,t,o={},n)=>{const r=B.find(a=>a.artifactId===e),s=lk(Cl(i),o,r?.duration??null);L(n,!1,()=>le(null)),L(n,!1,()=>O(null)),L(n,!0,()=>{nl(i,s.platform,o),Te({assetId:e,targetLabel:t,mediaUrl:r?.mediaUrl??null,thumbnailUrl:r?.thumbnailUrl??null,width:r?.width??null,height:r?.height??null,durationSeconds:r?.duration??null,platform:s.platform,identities:{x:{handle:s.handles?.x??"",recent:[]},tiktok:{handle:s.handles?.tiktok??"",recent:[]}},url:s.url??"",includeQr:s.includeQr??!0,includeHandle:s.includeHandle??!0,position:s.position??"auto",handleVerticalPercent:s.handleVerticalPercent===void 0?uk:_l(s.handleVerticalPercent),handlePlacement:s.handlePlacement??"center",includePlatformIcon:s.includePlatformIcon??!0,includeHandleBorder:s.includeHandleBorder??!0,handlePadding:s.handlePadding===void 0?xl:cr(s.handlePadding),handlePaddingY:s.handlePaddingY===void 0?xl:cr(s.handlePaddingY),handleRounding:s.handleRounding===void 0?dk:Al(s.handleRounding),qrOpacity:s.qrOpacity===void 0?Sl:lr(s.qrOpacity),handleOpacity:s.handleOpacity===void 0?Sl:lr(s.handleOpacity),qrStartSeconds:s.qrStartSeconds??0,qrEndSeconds:s.qrEndSeconds??null,handleStartSeconds:s.handleStartSeconds??0,handleEndSeconds:s.handleEndSeconds??null,fadeSeconds:s.fadeSeconds===void 0?ck:El(s.fadeSeconds),saveDefault:s.saveDefault??!1,loadingConfig:!0,error:null})}),Promise.allSettled(fk.map(async a=>{const l=D(await w("get_watermark_config",{book_id:i,platform:a},{background:!0,chat:n})),u=_(l?.savedHandle),d=_(l?.authenticatedHandle),p=Array.isArray(l?.recent)?l.recent.filter(R=>typeof R=="string"):[],v=D(l?.profile),S=_(v?.handle),A=_(v?.profileUrl),y=Cl(i).handles?.[a];M(n,()=>Te(R=>R&&R.assetId===e?{...R,url:R.url||(a===R.platform?A??"":R.url),identities:{...R.identities,[a]:{handle:y??(R.identities[a].handle||(u??d??p[0]??S??"")),recent:p}}}:R))})).then(()=>{M(n,()=>Te(a=>a&&a.assetId===e?{...a,loadingConfig:!1}:a))})},Vd=async e=>{if(!i||!he)return{ok:!1,message:"There is no pending watermark to apply."};const{assetId:t,targetLabel:o,platform:n,identities:r,url:s,includeQr:a,includeHandle:l,position:u,handleVerticalPercent:d,handlePlacement:p,includePlatformIcon:v,includeHandleBorder:S,handlePadding:A,handlePaddingY:y,handleRounding:R,qrOpacity:q,handleOpacity:V,qrStartSeconds:X,qrEndSeconds:P,handleStartSeconds:N,handleEndSeconds:H,fadeSeconds:te,saveDefault:de}=he,pe=r[n].handle.trim().replace(/^@/,"").trim(),He=s.trim();if(!a&&!l)return{ok:!1,message:"Include a QR code, a handle, or both before applying the watermark.",nextInput:"/apply",selectInput:!1};if(l&&!pe)return{ok:!1,message:"Enter a handle before applying the watermark.",nextInput:"/apply",selectInput:!1};if(a&&!He&&!pe)return{ok:!1,message:"Enter a QR link before applying the watermark.",nextInput:"/apply",selectInput:!1};M(e,()=>Te(be=>be&&be.assetId===t?{...be,error:null}:be)),T(!0);try{const be=D(await w("apply_watermark",{book_id:i,asset_id:t,platform:n,...pe&&(l||!He)?{handle:pe}:{},include_qr:a,include_handle:l,position:u,...l?{handle_vertical_percent:d}:{},...l&&a&&p!=="center"?{handle_position:p}:{},...l?{include_platform_icon:v}:{},...l?{include_handle_border:S}:{},...l?{handle_padding:A}:{},...l?{handle_padding_y:y}:{},...l?{handle_rounding:R}:{},...l?{handle_opacity:V}:{},...a&&He?{url:He}:{},...a?{qr_opacity:q}:{},...a&&X>0?{qr_start_seconds:X}:{},...a&&P!==null?{qr_end_seconds:P}:{},...l&&N>0?{handle_start_seconds:N}:{},...l&&H!==null?{handle_end_seconds:H}:{},fade_seconds:te,...l&&de?{save_default:!0}:{},wait:!1},{chat:e})),Oe={includeQr:a,includeHandle:l,handle:pe,handlePlacement:p,handleVerticalPercent:d,handleOpacity:V,qrOpacity:q,requestedPosition:u},Zt=ie(be?.job_id);if(_(be?.status)==="accepted"&&Zt!==null){const Mi=Ek(a,l,pe,o);return M(e,()=>h(Mi)),L(e,!1,()=>Te(null)),Wd({bookId:i,artifactId:t,jobId:Zt,targetLabel:o,describe:Ti=>Rl({...Oe,corner:_(Ti?.corner),placementSource:_(Ti?.placementSource)})},e),{ok:!0,message:Mi}}await F(i,c?.id,void 0,e);const Pi=Rl({...Oe,corner:_(be?.position),placementSource:_(be?.placement_source)});return M(e,()=>h(Pi)),L(e,!1,()=>Te(null)),{ok:!0,message:Pi}}catch(be){const Oe=be instanceof Error?be.message:String(be);return M(e,()=>Te(Zt=>Zt&&Zt.assetId===t?{...Zt,error:Oe}:Zt)),M(e,()=>h(Oe,"error")),{ok:!1,message:Oe,nextInput:"/apply",selectInput:!1}}finally{T(!1)}},Gd=async e=>{if(!(e.length===0||!i)){if(Ec){h("Wait for the current import to finish");return}da(!0);try{let t=0,o=0;for(const r of e){const s=await Xl(r),a=D(await w("check_duplicate_bytes",{book_id:i,object_hash:s})),l=Array.isArray(a?.matches)?a.matches:[];if(l.length>0){const p=D(l[0]),v=_(p?.label)??_(p?.artifact_id)??"existing source";if(!window.confirm(`${r.name} has the same bytes as ${v}.
|
|
16
|
+
This removes the cells and their connections. This cannot be undone.`))return;const u=new Set,d=()=>{const p=It.map(v=>v.id).filter(v=>!u.has(v)).at(-1)??null;wo(new Set([...lt.current].filter(v=>!u.has(v)))),qo(v=>v&&!u.has(v)?v:p),Le(v=>v&&u.has(v)?null:v)};ta(n),ht(p=>p.map(v=>n.has(v.id)?{...v,data:{...v.data,deleting:!0}}:v)),T(!0);try{await rt(180);for(const p of o)await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:p.id}),u.add(p.id);Y&&u.has(Y.cellId)&&Kt(),await F(i,c.id),d(),h(s===1?`${r[0]} deleted`:`${s} cells deleted`)}catch(p){Y&&u.has(Y.cellId)&&Kt(),await F(i,c.id).catch(()=>{}),d();const v=p instanceof Error?p.message:String(p);h(u.size>0?`Deleted ${u.size} of ${s} cells. ${v}`:v,"error")}finally{ht(p=>p.map(v=>n.has(v.id)?{...v,data:{...v.data,deleting:!1}}:v)),ta(new Set),T(!1)}},Td=async()=>{$&&await xo([$])},Va=async()=>{await xo(It)},jd=e=>{if(e.key!=="Backspace"&&e.key!=="Delete")return;const t=e.target;t instanceof HTMLElement&&t.closest('input, textarea, select, button, a, [contenteditable="true"]')||G||It.length===0||(e.preventDefault(),e.stopPropagation(),Va())},$d=async e=>{if(!(!i||!c))try{await w("move_notebook_cells",{book_id:i,notebook_id:c.id,slots:e.map(t=>({id:t.id,row:t.data.slot.row,column:t.data.slot.column}))}),await $e(i,c.id)}catch(t){const o=t instanceof Error?t.message:String(t);await $e(i,c.id).catch(()=>{}),h(o,"error")}},qd=async()=>{if(!(!i||!c||c.cells.length===0)){T(!0);try{const e=ge(await w("get_notebook",{book_id:i,notebook_id:c.id}));if(!e)throw new Error("Unable to read the notebook before arranging");if(Q.current.bookId!==i||Q.current.notebookId!==c.id)return;const t=rg(e);if(!t.ok)throw new Error(t.message);const o=new Map(e.cells.map(a=>[a.id,a.slot])),n=t.slots.some(a=>{const l=o.get(a.id);return l?.row!==a.row||l?.column!==a.column}),r=()=>sg(()=>Ut.current);if(!n){await $e(i,c.id),h("Notebook is already auto-arranged"),r();return}await w("move_notebook_cells",{book_id:i,notebook_id:c.id,...e.revision?{expected_revision:e.revision}:{},slots:t.slots}),await $e(i,c.id);const s=Me?t.slots.find(a=>a.id===Me):void 0;s&&Ae({row:s.row,column:s.column}),h(`Auto-arranged ${t.slots.length} ${t.slots.length===1?"tile":"tiles"}`),r()}catch(e){await $e(i,c.id).catch(()=>{}),h(e instanceof Error?e.message:String(e),"error")}finally{T(!1)}}},Nd=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"No notebook is open"};const n=Lk(c,ld,t,e);if(!n.ok)return M(o,()=>h(n.message,"error")),{ok:!1,message:n.message};const r=e==="column"?`column ${t.column+1}`:`row ${String.fromCharCode(97+t.row)}`;if(n.movedCount===0){const a=`Videos are already arranged in ${r}`;return M(o,()=>h(a)),{ok:!0,message:a}}const s=_(D(c)?.revision);T(!0);try{await w("move_notebook_cells",{book_id:i,notebook_id:c.id,...s?{expected_revision:s}:{},slots:n.slots},{chat:o}),await $e(i,c.id,o),Ae({row:t.row,column:t.column});const a=n.slots.length-n.displacedCount,l=`Arranged ${a} ${a===1?"video":"videos"} in ${r}`;return M(o,()=>h(l)),{ok:!0,message:l}}catch(a){await $e(i,c.id,o).catch(()=>{});const l=a instanceof Error?a.message:String(a);return M(o,()=>h(l,"error")),{ok:!1,message:l}}finally{T(!1)}},Ga=async(e,t)=>{if(!i||!c)return{ok:!1,message:"No notebook is open"};const o=ok(c,Ma,e);if(!o.ok)return M(t,()=>h(o.message,"error")),{ok:!1,message:o.message};const n=W(e);if(o.movedCount===0){const s=`Images are already grouped from ${n}`;return M(t,()=>h(s)),{ok:!0,message:s}}const r=_(D(c)?.revision);T(!0);try{await w("move_notebook_cells",{book_id:i,notebook_id:c.id,...r?{expected_revision:r}:{},slots:o.slots},{chat:t}),await $e(i,c.id,t),Ae({row:e.row,column:e.column});const s=o.slots.length-o.displacedCount,a=`Grouped ${s} ${s===1?"image":"images"} from ${n}`;return M(t,()=>h(a)),{ok:!0,message:a}}catch(s){await $e(i,c.id,t).catch(()=>{});const a=s instanceof Error?s.message:String(s);return M(t,()=>h(a,"error")),{ok:!1,message:a}}finally{T(!1)}},Ld=async e=>{if(!(!i||!c||!e.source||!e.target)){if(!ll(c.edges,e,c.cells)){const t=c.cells.find(n=>n.id===e.source),o=c.cells.find(n=>n.id===e.target);h(t&&o?`Connecting ${W(t.slot)} to ${W(o.slot)} would create a cycle`:"That connection would create a cycle","error");return}T(!0);try{await w("connect_notebook_cells",{book_id:i,notebook_id:c.id,source_cell_id:e.source,target_cell_id:e.target,target_input:pl(c,e)}),await $e(i,c.id),h("Cells connected")}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{T(!1)}}},Fd=async e=>{if(!(!i||!c||e.length===0))try{await Promise.all(e.map(t=>w("disconnect_notebook_cells",{book_id:i,notebook_id:c.id,edge_id:t}))),await $e(i,c.id),h("Connection removed")}catch(t){h(t instanceof Error?t.message:String(t),"error")}},Ua=async(e,t)=>{if(!i)throw new Error("Choose a book before uploading media");const o=await Xl(e),n=D(await w("check_duplicate_bytes",{book_id:i,object_hash:o})),s=(Array.isArray(n?.matches)?n.matches:[]).map(p=>D(p)).find(p=>{const v=p&&_(p.kind);return v!==null&&Vs(t,v)}),a=s&&_(s.artifact_id);if(a)return{artifactRef:a,reusedExisting:!0};const l=await fetch(`/api/books/${encodeURIComponent(i)}/upload?filename=${encodeURIComponent(e.name)}`,{method:"POST",body:e}),u=D(await l.json());if(!l.ok)throw new Error(_(u?.error)??`Upload failed: ${e.name}`);const d=_(u?.assetId);if(!d)throw new Error("Upload did not return an asset id");return{artifactRef:d,reusedExisting:!1}},Wa=async(e,t)=>{if(!i||!c||g.state!=="ready")return;const o=nr(),n=c.cells.find(a=>a.id===e),r=n&&Ft(n.type);if(!n||!r)return;if(n.outputArtifactId||c.edges.some(a=>a.target===e)){Zo(e,"This media slot already contains media.");return}if(Rs(t)!==r){Zo(e,`Choose one ${r} file for this slot.`);return}Rt(e,"upload");try{const{artifactRef:a,reusedExisting:l}=await Ua(t,r);await w("set_notebook_media_slot",{book_id:i,notebook_id:c.id,cell_id:e,artifact_ref:a}),await F(i,c.id),Rt(e,null),h(l?`Reused @${a} in media slot`:`Uploaded and attached @${a}`),Nn({bookId:i,notebookId:c.id,cellId:e,address:Se(n.slot),artifactId:a})}catch(a){const l=a instanceof Error?a.message:String(a);Zo(e,l),h(l,"error")}finally{o()}},ts=async(e,t)=>{if(!i||!c)return;const o=nr();if(G){h("Wait for the current operation to finish","error");return}const n=Rs(t);if(!n){h("Drop an image, video, or audio file on an open square","error");return}if(vt.some(l=>l.row===e.row&&l.column===e.column)){h("Choose an empty grid square for the media file","error");return}const r=W(e);let s=null,a=!1;T(!0);try{const{artifactRef:l,reusedExisting:u}=await Ua(t,n),d=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:{type:n,slot:e}}));if(s=d&&_(d.id),!s)throw new Error("The server did not return the new media cell");await w("set_notebook_media_slot",{book_id:i,notebook_id:c.id,cell_id:s,artifact_ref:l}),a=!0,z?.cellId===null&&zn(),ae(),Ae(e),await F(i,c.id),h(u?`Reused @${l} at ${r}`:`Uploaded and attached @${l} at ${r}`),Nn({bookId:i,notebookId:c.id,cellId:s,address:Se(e),artifactId:l})}catch(l){let u=l instanceof Error?l.message:String(l);if(s&&!a)try{await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:s})}catch(d){const p=d instanceof Error?d.message:String(d);u=`${u}. The empty ${r} cell could not be removed: ${p}`}await F(i,c.id).catch(()=>{}),h(u,"error")}finally{T(!1),o()}},zn=()=>{const e=Lg(Fr.current);_e.current+=1,fe.lifecycle.close(),ke(null),Fr.current=null,e()},Ct=async(e,t,o,n,r,s,a)=>{const l=c?.cells.find(S=>S.id===e),u=a??(e===null?"all":l&&Ft(l.type));if(!u)return;const d=r??(z?.cellId===e?Jb(fe.state):{mode:"text",reference:null,referenceStartSeconds:"0",referenceDurationSeconds:""}),p=s??(z?.cellId===e?z.tagFilters:[]),v=_e.current+1;_e.current=v,ke(S=>!S||S.cellId!==e?S:{...S,query:t,tagFilters:[...p],assets:n?S.assets:[],page:n?S.page:mr,booksWithErrors:n?S.booksWithErrors:[],preparingIndex:!1,loading:!n,loadingMore:n,error:null});try{let S;try{S=d.mode==="video-reverse"&&d.reference?jg(d.referenceStartSeconds,d.referenceDurationSeconds,d.reference):void 0}catch(q){const V=fe.lifecycle.getState().reference===d.reference?fe.lifecycle.resetInvalidRange(q):q instanceof Error?q.message:String(q);throw new Error(V)}const A=()=>_e.current!==v,y=await $g({search:()=>w("search_library_assets",{...d.mode==="text"&&t.trim()?{query:t.trim()}:{},...d.mode!=="text"&&d.reference?{reference_id:d.reference.referenceId}:{},...S?{reference_range:S}:{},kinds:u==="all"?["audio","image","video"]:[u],...qg(p),limit:mr.limit,offset:o}),listJobs:(q,V)=>w("list_jobs",{book_id:q,job_ids:V},{background:!0}),onPreparing:q=>{A()||ke(V=>V&&V.cellId===e?{...V,preparingIndex:q}:V)},isCancelled:A});if(A())return;const R=Ng(y);ke(q=>{if(!q||q.cellId!==e)return q;const V=R.assets.filter(N=>Vs(u,N.type)),X=n?[...q.assets,...V]:V,P=new Map(X.map(N=>[`${N.owningBookId}:${N.artifactId}`,N]));return{...q,assets:[...P.values()],page:R.page,booksWithErrors:R.booksWithErrors,unindexedVisualAssets:R.unindexedVisualAssets,loading:!1,loadingMore:!1}})}catch(S){if(_e.current!==v)return;const A=S instanceof Error?S.message:String(S);ke(y=>y&&y.cellId===e?{...y,loading:!1,loadingMore:!1,error:A}:y),h(A,"error")}},za=(e,t=c)=>{const o=t?.cells.find(r=>r.id===e),n=o?Ft(o.type):null;return!o||!n||o.outputArtifactId||t?.edges.some(r=>r.target===e)?null:n},Eo=(e,t=c,o)=>{if(!t||g.state!=="ready")return;const n=e===null?"all":za(e,t);n&&((e===null||lt.current.size!==1||!lt.current.has(e))&&Z(e),Le(null),kt(null),me(!0),Fr.current=document.activeElement instanceof HTMLElement?document.activeElement:null,fe.lifecycle.close(),e&&Rt(e,null),ke({unindexedVisualAssets:0,preparingIndex:!1,bookId:i,notebookId:t.id,cellId:e,slot:o,query:"",draftQuery:"",assets:[],page:mr,booksWithErrors:[],loading:!0,loadingMore:!1,error:null,activeArtifactId:null,tagFilters:[],tagSuggestions:[]}),Ct(e,"",0,!1,{mode:"text",reference:null,referenceStartSeconds:"0",referenceDurationSeconds:""},[],n))},Dd=()=>{zn(),me(!1)},os=e=>{Qt("notebook"),Eo(null,c,e)},Od=async e=>{if(!i||!c||!z||g.state!=="ready"||G)return;const t=z,o=_e.current,n=()=>_e.current===o&&Q.current.bookId===t.bookId&&Q.current.notebookId===t.notebookId;let r=t.cellId;const s=c.cells.find(d=>d.id===r),a=r===null?Os(e.type):s&&Ft(s.type);if(!a||!Vs(a,e.type))return;r&&Rt(r,"attach"),ke(d=>d===t?{...d,activeArtifactId:e.artifactId,error:null}:d);let l=null,u=!1;T(!0);try{if(r===null){const d=t.slot??Mo(a,c.cells,Ge),p=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:{type:a,slot:d}}));if(l=p&&_(p.id),!l)throw new Error("The server did not return the new media cell");r=l,Ae(d)}if(e.owningBookId===i?await w("set_notebook_media_slot",{book_id:i,notebook_id:c.id,cell_id:r,artifact_ref:e.artifactId}):await w("attach_library_asset",{source_book_id:e.owningBookId,source_artifact_id:e.artifactId,target_book_id:i,notebook_id:c.id,cell_id:r,expected_output_artifact_id:s?.outputArtifactId??null}),u=!0,!n()||(await F(i,c.id),!n()))return;Rt(r,null),h(e.owningBookId===i?`Attached @${e.id}`:`Copied and attached @${e.id} from ${e.owningBookName}`),(t.cellId!==null||lt.current.size===0)&&(zn(),l&&ae())}catch(d){let p=d instanceof Error?d.message:String(d);if(l&&!u)try{await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:l})}catch(v){p+=`. The empty cell could not be removed: ${v instanceof Error?v.message:String(v)}`}if(!n())return;t.cellId&&Zo(t.cellId,p),ke(v=>v&&v.cellId===t.cellId?{...v,activeArtifactId:null,error:p}:v),h(p,"error")}finally{!n()&&t.cellId&&Q.current.bookId===t.bookId&&Rt(t.cellId,null),T(!1)}},Hn=kp({callTool:w,ready:g.state==="ready"}),Vd=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before speaking."};let n=null,r=!1;try{if(!_t)throw new Error("Offline: cloud generation is unavailable. Local search, editing, playback, and export remain available.");const s=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(!s)throw new Error("The server returned an invalid notebook");const a=await Fk({bookId:i,callTool:(y,R)=>w(y,R,{chat:o}),document:s,lastWorkSlot:Ge,text:e,voiceId:t,...s.revision?{expectedRevision:s.revision}:{}});n=a;const l=jl(a.cellAddress);l&&Ae(l);const u=await bo(a.cellId,"slash",o),d=u.stages.find(y=>y.kind==="queued"&&y.jobType==="generation"&&y.tool==="run_notebook_cell"&&y.input.cell_id===a.cellId);if(d?.kind!=="queued")throw new Error("The generation plan is missing its notebook cell");const p=_(d.input.notebook_id);if(p!==s.id)throw new Error("The generation plan belongs to another notebook");if(!ur(d))throw new Error("Cloud generation cancelled before sending data");L(o,!1,()=>O(null)),L(o,!1,()=>le(null));const v=await er({start:()=>w("run_notebook_cell",{book_id:i,notebook_id:p,cell_id:a.cellId,plan:u,actor:"videobook-user"},{chat:o}),onStarting:()=>oe(a.cellId,!0),onRejected:()=>oe(a.cellId,!1)}),S=_(D(v)?.run_id),A=_(D(v)?.job_id);if(!S||!A)throw oe(a.cellId,!1),new Error("The server did not return a notebook run");return r=!0,Dk(t),ae(o),M(o,()=>h(`${a.cellAddress} queued`)),tn({bookId:i,notebookId:p,cellId:a.cellId,address:a.cellAddress.replace(/^@/,""),runId:S,jobOperationId:A},o),await F(i,c.id,void 0,o).catch(()=>{}),{ok:!0,message:`${a.cellAddress} queued`}}catch(s){const a=s instanceof Error?s.message:String(s);return n&&!r?(await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:n.cellId},{chat:o}).catch(()=>{}),await w("delete_notebook_cell",{book_id:i,notebook_id:c.id,cell_id:n.outputCellId},{chat:o}).catch(()=>{}),{ok:!1,message:a}):r?(M(o,()=>h(a,"error")),{ok:!1,message:a}):{ok:!1,message:a}}},Ha=(e,t,o={},n)=>{const r=H.find(a=>a.artifactId===e),s=uk(Cl(i),o,r?.duration??null);L(n,!1,()=>le(null)),L(n,!1,()=>O(null)),L(n,!0,()=>{nl(i,s.platform,o),Te({assetId:e,targetLabel:t,mediaUrl:r?.mediaUrl??null,thumbnailUrl:r?.thumbnailUrl??null,width:r?.width??null,height:r?.height??null,durationSeconds:r?.duration??null,platform:s.platform,identities:{x:{handle:s.handles?.x??"",recent:[]},tiktok:{handle:s.handles?.tiktok??"",recent:[]}},url:s.url??"",includeQr:s.includeQr??!0,includeHandle:s.includeHandle??!0,position:s.position??"auto",handleVerticalPercent:s.handleVerticalPercent===void 0?pk:_l(s.handleVerticalPercent),handlePlacement:s.handlePlacement??"center",includePlatformIcon:s.includePlatformIcon??!0,includeHandleBorder:s.includeHandleBorder??!0,handlePadding:s.handlePadding===void 0?xl:cr(s.handlePadding),handlePaddingY:s.handlePaddingY===void 0?xl:cr(s.handlePaddingY),handleRounding:s.handleRounding===void 0?mk:Al(s.handleRounding),qrOpacity:s.qrOpacity===void 0?Sl:lr(s.qrOpacity),handleOpacity:s.handleOpacity===void 0?Sl:lr(s.handleOpacity),qrStartSeconds:s.qrStartSeconds??0,qrEndSeconds:s.qrEndSeconds??null,handleStartSeconds:s.handleStartSeconds??0,handleEndSeconds:s.handleEndSeconds??null,fadeSeconds:s.fadeSeconds===void 0?fk:El(s.fadeSeconds),saveDefault:s.saveDefault??!1,loadingConfig:!0,error:null})}),Promise.allSettled(gk.map(async a=>{const l=D(await w("get_watermark_config",{book_id:i,platform:a},{background:!0,chat:n})),u=_(l?.savedHandle),d=_(l?.authenticatedHandle),p=Array.isArray(l?.recent)?l.recent.filter(R=>typeof R=="string"):[],v=D(l?.profile),S=_(v?.handle),A=_(v?.profileUrl),y=Cl(i).handles?.[a];M(n,()=>Te(R=>R&&R.assetId===e?{...R,url:R.url||(a===R.platform?A??"":R.url),identities:{...R.identities,[a]:{handle:y??(R.identities[a].handle||(u??d??p[0]??S??"")),recent:p}}}:R))})).then(()=>{M(n,()=>Te(a=>a&&a.assetId===e?{...a,loadingConfig:!1}:a))})},Gd=async e=>{if(!i||!he)return{ok:!1,message:"There is no pending watermark to apply."};const{assetId:t,targetLabel:o,platform:n,identities:r,url:s,includeQr:a,includeHandle:l,position:u,handleVerticalPercent:d,handlePlacement:p,includePlatformIcon:v,includeHandleBorder:S,handlePadding:A,handlePaddingY:y,handleRounding:R,qrOpacity:q,handleOpacity:V,qrStartSeconds:X,qrEndSeconds:P,handleStartSeconds:N,handleEndSeconds:B,fadeSeconds:te,saveDefault:de}=he,pe=r[n].handle.trim().replace(/^@/,"").trim(),Be=s.trim();if(!a&&!l)return{ok:!1,message:"Include a QR code, a handle, or both before applying the watermark.",nextInput:"/apply",selectInput:!1};if(l&&!pe)return{ok:!1,message:"Enter a handle before applying the watermark.",nextInput:"/apply",selectInput:!1};if(a&&!Be&&!pe)return{ok:!1,message:"Enter a QR link before applying the watermark.",nextInput:"/apply",selectInput:!1};M(e,()=>Te(be=>be&&be.assetId===t?{...be,error:null}:be)),T(!0);try{const be=D(await w("apply_watermark",{book_id:i,asset_id:t,platform:n,...pe&&(l||!Be)?{handle:pe}:{},include_qr:a,include_handle:l,position:u,...l?{handle_vertical_percent:d}:{},...l&&a&&p!=="center"?{handle_position:p}:{},...l?{include_platform_icon:v}:{},...l?{include_handle_border:S}:{},...l?{handle_padding:A}:{},...l?{handle_padding_y:y}:{},...l?{handle_rounding:R}:{},...l?{handle_opacity:V}:{},...a&&Be?{url:Be}:{},...a?{qr_opacity:q}:{},...a&&X>0?{qr_start_seconds:X}:{},...a&&P!==null?{qr_end_seconds:P}:{},...l&&N>0?{handle_start_seconds:N}:{},...l&&B!==null?{handle_end_seconds:B}:{},fade_seconds:te,...l&&de?{save_default:!0}:{},wait:!1},{chat:e})),Oe={includeQr:a,includeHandle:l,handle:pe,handlePlacement:p,handleVerticalPercent:d,handleOpacity:V,qrOpacity:q,requestedPosition:u},eo=ie(be?.job_id);if(_(be?.status)==="accepted"&&eo!==null){const Mi=Rk(a,l,pe,o);return M(e,()=>h(Mi)),L(e,!1,()=>Te(null)),zd({bookId:i,artifactId:t,jobId:eo,targetLabel:o,describe:Ti=>Rl({...Oe,corner:_(Ti?.corner),placementSource:_(Ti?.placementSource)})},e),{ok:!0,message:Mi}}await F(i,c?.id,void 0,e);const Pi=Rl({...Oe,corner:_(be?.position),placementSource:_(be?.placement_source)});return M(e,()=>h(Pi)),L(e,!1,()=>Te(null)),{ok:!0,message:Pi}}catch(be){const Oe=be instanceof Error?be.message:String(be);return M(e,()=>Te(eo=>eo&&eo.assetId===t?{...eo,error:Oe}:eo)),M(e,()=>h(Oe,"error")),{ok:!1,message:Oe,nextInput:"/apply",selectInput:!1}}finally{T(!1)}},Ud=async e=>{if(!(e.length===0||!i)){if(Ec){h("Wait for the current import to finish");return}da(!0);try{let t=0,o=0;for(const r of e){const s=await Xl(r),a=D(await w("check_duplicate_bytes",{book_id:i,object_hash:s})),l=Array.isArray(a?.matches)?a.matches:[];if(l.length>0){const p=D(l[0]),v=_(p?.label)??_(p?.artifact_id)??"existing source";if(!window.confirm(`${r.name} has the same bytes as ${v}.
|
|
17
17
|
|
|
18
|
-
Choose OK to import another copy, or Cancel to reuse the existing source.`)){o+=1;continue}}const u=await fetch(`/api/books/${encodeURIComponent(i)}/upload?filename=${encodeURIComponent(r.name)}`,{method:"POST",body:r}),d=await u.json();if(!u.ok)throw new Error(d.error??`Upload failed: ${r.name}`);t+=1}const n=await F(i,c?.id);ir(c,n)&&ae(),h([t>0?`Imported ${t}`:"",o>0?`reused ${o} existing`:""].filter(Boolean).join(" · ")||"No files imported")}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{da(!1)}}},
|
|
18
|
+
Choose OK to import another copy, or Cancel to reuse the existing source.`)){o+=1;continue}}const u=await fetch(`/api/books/${encodeURIComponent(i)}/upload?filename=${encodeURIComponent(r.name)}`,{method:"POST",body:r}),d=await u.json();if(!u.ok)throw new Error(d.error??`Upload failed: ${r.name}`);t+=1}const n=await F(i,c?.id);ir(c,n)&&ae(),h([t>0?`Imported ${t}`:"",o>0?`reused ${o} existing`:""].filter(Boolean).join(" · ")||"No files imported")}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{da(!1)}}},Wd=e=>{const t=[...e.target.files??[]];e.target.value="",Ud(t)},zd=m.useCallback(async(e,t)=>{const o=Date.now()+Wl;let n=0,r=0;const s=async(a,l="info")=>{try{await F(e.bookId,Q.current.notebookId??void 0,void 0,t)}catch{}M(t,()=>h(a,l))};for(;Date.now()<o;){const a=Q.current;if(a.bookId!==e.bookId)return;try{const l=performance.now(),u=a.notebookId,[d,p,v]=await Promise.all([Pe.current("list_assets",{book_id:e.bookId,sort:"newest",limit:200,include_referenced:!0},{background:!0}),Pe.current("list_jobs",{book_id:e.bookId,limit:200},{background:!0}),u?Pe.current("get_notebook",{book_id:e.bookId,notebook_id:u},{background:!0}):Promise.resolve(null)]);n=0;const S=Q.current;if(S.bookId!==e.bookId)return;const A=Lt(d),y=oo(p),R=u&&S.notebookId===u?ge(v):null;l>=ye.current&&(ye.current=l,Je(V=>Nt(V,A)?V:A),ct(y),R&&Ie(R,A,y));const q=bp(e.artifactId,e.jobId,A.find(V=>V.artifactId===e.artifactId),y);if(q.kind==="completed"){await s(e.describe(q.result));return}if(q.kind==="failed"){await s(q.message,"error");return}if(r=q.kind==="missing"?r+1:0,r>=nw){M(t,()=>h(`Lost track of the ${e.targetLabel} watermark job — check the Jobs screen`,"error"));return}}catch(l){if(n+=1,n>=10){const u=l instanceof Error?l.message:String(l);M(t,()=>h(`Stopped watching the ${e.targetLabel} watermark: ${u}. Check the Jobs screen.`,"error"));return}}await rt(Ul)}M(t,()=>h(`${e.targetLabel} watermark is still processing — check the Jobs screen`))},[ct,Ie,F,h]),Ba=async e=>{if(i){T(!0);try{await w("cancel_job",{book_id:i,job_id:e}),await F(i,c?.id),h(`Job ${e} cancelled`)}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{T(!1)}}},Hd=async e=>{if(i){T(!0);try{await w("retry_job",{book_id:i,job_id:e}),await F(i,c?.id),h(`Job ${e} retry queued`)}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{T(!1)}}},Bd=async(e,t)=>{if(!i||!c)return;const o=e.plan.stages.find(r=>r.kind==="queued"&&r.jobType==="generation"),n=t==="switch"?window.prompt("Generation model",o?.kind==="queued"?o.tool:"")?.trim():void 0;if(!(t==="switch"&&!n)){T(!0);try{const r=await w("revise_notebook_generation_plan",{book_id:i,notebook_id:c.id,plan_id:e.planId,action:t,...n?{model:n}:{},source_surface:"ui",actor:"videobook-user"});t==="omit"?(await F(i,c.id),h("Generation output omitted; the preserved failure remains available")):(O(null),le({plan:ft(r),previews:{}}),h(t==="retry"?"Retry plan ready for review":"Provider/model switch ready for review"))}catch(r){h(r instanceof Error?r.message:String(r),"error")}finally{T(!1)}}},Kd=async e=>{if(!(!i||!c)){T(!0);try{const t=await w("continue_notebook_generation",{book_id:i,notebook_id:c.id,plan_id:e.planId,actor:"videobook-user"}),o=D(t);if(o?.kind==="stale-continuation"){h(_(o.message)??"The sequence changed; review a new destination","error"),await F(i,c.id);return}const n=await Xt(ft(t));h(n.message,n.ok?"info":"error")}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{T(!1)}}},Ka=async(e={})=>{try{const t=await Yg(w,e);return so(o=>({...o,status:t,error:null})),Ra(Zn(t)),t}catch(t){return so(o=>({...o,error:t instanceof Error?t.message:String(t)})),null}},ns=async()=>{if($o.connecting)return{ok:!1,message:"X authorization is already waiting for approval."};so(e=>({...e,connecting:!0,authorizeUrl:null,error:null}));try{const e=await Xp(w);so(n=>({...n,authorizeUrl:e})),window.open(e,"_blank","noopener,noreferrer");const t=await Qp(w,{sleep:rt}),o=Yp(t);return so({status:t,connecting:!1,authorizeUrl:null,error:o.ok||t.error?null:o.message}),Ra(Zn(t)),h(o.message,o.ok?"info":"error"),o}catch(e){const t=e instanceof Error?e.message:String(e);return so(o=>({...o,connecting:!1,authorizeUrl:null,error:t})),h(t,"error"),{ok:!1,message:t}}},ln=async()=>{if(g.state!=="ready")return;const e=++Zs.current,t=i;Xs(!0),Qs(null),Do(null),Ys(!1),yr(t?{bookId:t,status:"loading"}:null);const[o,n,r]=await Promise.allSettled([w("provider_key_status",{}),t?w("storage_status",{book_id:t}):Promise.resolve(null),Ka({refreshAccount:!0})]);if(e!==Zs.current)return;let s=!0;try{if(o.status==="rejected")throw o.reason;dc(gg(o.value))}catch(a){s=!1,Qs(a instanceof Error?a.message:String(a))}if(t)try{if(n.status==="rejected")throw n.reason;yr({bookId:t,status:"ready",value:kg(n.value)})}catch(a){s=!1,yr({bookId:t,status:"error",error:a instanceof Error?a.message:String(a)})}Ys(s&&r.status==="fulfilled"&&r.value!==null),Xs(!1)},Jd=async(e,t)=>{if(g.state!=="ready")throw new Error("Connect to save settings");if(!t.trim())throw new Error("Enter a value to save");T(!0);try{await w("set_env_secret",{key:e,value:t}),await ln()}finally{T(!1)}},Xt=async(e,t)=>{try{const o=e.stages.filter(a=>a.kind==="edit"),n=await Promise.all(o.map(async a=>[a.stageId,await w("preview_edit_intent",{book_id:i,intent:a.intent},{chat:t})])),r=Object.fromEntries(n);L(t,!1,()=>O(null)),L(t,!0,()=>le({plan:e,previews:r}));const s=Object.values(r).reduce((a,l)=>a+l.conflicts.length,0);return s>0?{ok:!1,message:`Plan requires review: ${s} conflicts`}:pt("Plan preview ready")}catch(o){return{ok:!1,message:o instanceof Error?o.message:String(o)}}},Xd=async e=>{if(!ue?.plan.suggestions)return;const t=ue.plan.suggestions.map(s=>s.suggestionId===e?{...s,included:!s.included}:s),o=t.filter(s=>s.included).map(s=>s.operation),n={...ue.plan,suggestions:t,stages:ue.plan.stages.map(s=>s.kind==="edit"?{...s,intent:{...s.intent,operations:o}}:s)};if(o.length===0){le({plan:n,previews:{}});return}const r=await Xt(n);h(r.message,r.ok?"info":"error")},Ja=async(e,t,o)=>{if(!i)return{ok:!1,message:"Load or create a book first."};try{const n=ft(await w("plan_sequence_edit",{book_id:i,source_surface:t,actor:"videobook-user",edits:Array.isArray(e)?e:[e]},{chat:o}));return await Xt(n,o)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},Qd=async e=>{if(!i||!ue)return{ok:!1,message:"There is no pending command plan."};const t=ue;T(!0);try{const o=t.plan.stages.find(a=>a.kind==="queued"&&a.input.workbook_run===!0);if(o?.kind==="queued"){const a=t.plan.stages.some(S=>S.kind==="queued"&&S.jobType==="generation");if(a&&!_t)throw new Error("Offline: cloud generation is unavailable. The workbook plan remains preserved.");const l="videobook.cloud-generation-consent";if(a&&window.localStorage.getItem(l)!=="accepted"){if(!window.confirm(`Cloud generation disclosure
|
|
19
19
|
|
|
20
20
|
Payload class: rewritten prompts, extracted first and last frames, and connected media references.
|
|
21
21
|
The four scene audio assets remain local and replace generated sound after animation.
|
|
@@ -26,12 +26,12 @@ Provider/model: ${a.provider??"unknown"} · ${a.model??a.tool}
|
|
|
26
26
|
Payload class: prompt text and connected media references.
|
|
27
27
|
Your local source files are sent only when required by the selected model.
|
|
28
28
|
|
|
29
|
-
Continue and remember this choice on this device?`))throw new Error("Cloud generation cancelled before sending data");window.localStorage.setItem(l,"accepted")}const u=_(a.input.notebook_id),d=_(a.input.cell_id);if(!u||!d)throw new Error("The generation plan is missing its notebook cell");ne(d,null);const p=await er({start:()=>w("run_notebook_cell",{book_id:i,notebook_id:u,cell_id:d,plan:t.plan,actor:"videobook-user"},{chat:e}),onStarting:()=>oe(d,!0),onAccepted:()=>oe(d,!1),onRejected:()=>oe(d,!1)}),v=D(p),S=_(v?.run_id),A=_(v?.job_id),y=_(v?.output_cell_id);if(!S||!A)throw oe(d,!1),new Error("The server did not return a notebook run");y&&ae(e);const R=y??d,q=c?.cells.find(X=>X.id===d);let V=q?Se(q.slot):d.slice(0,8);if(y){const X=await w("get_notebook",{book_id:i,notebook_id:u},{background:!0,chat:e}),P=ge(X);if(P){Ie(P,
|
|
29
|
+
Continue and remember this choice on this device?`))throw new Error("Cloud generation cancelled before sending data");window.localStorage.setItem(l,"accepted")}const u=_(a.input.notebook_id),d=_(a.input.cell_id);if(!u||!d)throw new Error("The generation plan is missing its notebook cell");ne(d,null);const p=await er({start:()=>w("run_notebook_cell",{book_id:i,notebook_id:u,cell_id:d,plan:t.plan,actor:"videobook-user"},{chat:e}),onStarting:()=>oe(d,!0),onAccepted:()=>oe(d,!1),onRejected:()=>oe(d,!1)}),v=D(p),S=_(v?.run_id),A=_(v?.job_id),y=_(v?.output_cell_id);if(!S||!A)throw oe(d,!1),new Error("The server did not return a notebook run");y&&ae(e);const R=y??d,q=c?.cells.find(X=>X.id===d);let V=q?Se(q.slot):d.slice(0,8);if(y){const X=await w("get_notebook",{book_id:i,notebook_id:u},{background:!0,chat:e}),P=ge(X);if(P){Ie(P,H,Ve);const N=P.cells.find(B=>B.id===y);N&&(V=Se(N.slot))}M(e,()=>en([y])),ne(y,null),oe(y,!0)}tn({bookId:i,notebookId:u,cellId:R,address:V,runId:S,jobOperationId:A},e),r+=1;continue}if(a.kind==="queued")throw new Error(`Queued ${a.jobType} execution is not available from this plan yet`)}L(e,!1,()=>le(null)),co(n),await F(i,c?.id,void 0,e).catch(()=>{});const s=r>0?`CommandPlan accepted · ${r} queued job`:"CommandPlan committed to a new sequence revision";return M(e,()=>h(s)),{ok:!0,message:s}}catch(o){let n=o instanceof Error?o.message:String(o);M(e,()=>h(n,"error"));const r=t.plan.stages.some(a=>a.kind==="queued"&&a.jobType==="generation"),s=t.plan.stages.some(a=>a.kind==="export");if(!r&&!s)try{const a=await Ja(fw(t.plan.stages),t.plan.sourceSurface==="system"?"ui":t.plan.sourceSurface,e);a.ok||(n=a.message,M(e,()=>h(n,"error")))}catch{L(e,!1,()=>le(null)),n="The sequence changed. Recreate this plan against the current cut.",M(e,()=>h(n,"error"))}return{ok:!1,message:n,...r?{nextInput:"/apply",selectInput:!0}:{}}}finally{T(!1),M(e,()=>ko())}},Yd=async()=>{if(!(!i||!qr||!window.confirm(`Restore the sequence state before the last applied plan?
|
|
30
30
|
|
|
31
|
-
This creates a new forward revision.`))){T(!0);try{const t=D(await w("get_edit_action",{book_id:i,action_id:qr})),o=_(t?.baseRevision);if(!o)throw new Error("The edit audit has no base revision");const n=D(await w("restore_edit_action",{book_id:i,target_revision:o,base_revision:J?.revision??_(t?.committedRevision)??"",actor:"videobook-user",source_surface:"ui"}));lo(_(n?.actionId)??""),await F(i,c?.id),h("Restored the previous sequence state as a forward revision")}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{T(!1)}}},Yd=async(e,t)=>{if(!i||!c||!J)return{ok:!1,message:"Open a notebook sequence first."};const o=J.captions.slice(0,20).map(n=>({beat_id:n.cueId,text:n.text,timeline_start_frame:n.timelineStartFrame,duration_frames:n.durationFrames}));if(o.length===0)return{ok:!1,message:"Add captions first so narration beats have exact timing."};try{const n=await w("plan_notebook_rough_cut",{book_id:i,notebook_id:c.id,source_surface:e,actor:"videobook-user",beats:o,min_shot_frames:30,max_shot_frames:120,max_repeats_per_artifact:1},{chat:t}),r=D(n);return r?.kind==="rough-cut-uncovered"?{ok:!1,message:`No existing indexed coverage for ${Array.isArray(r.uncoveredBeats)?r.uncoveredBeats.length:o.length} narration beats.`}:await Xt(ft(n),t)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},Zd=async(e,t)=>{if(!i||!J)return{ok:!1,message:"Open a sequence first."};const o=J.captions.slice(0,20).map(n=>({beat_id:n.cueId,text:n.text,timeline_start_frame:n.timelineStartFrame,duration_frames:n.durationFrames}));if(o.length===0)return{ok:!1,message:"Add captions first so sound suggestions have exact timing."};try{const n=await w("plan_sequence_sound_effects",{book_id:i,source_surface:e,actor:"videobook-user",moments:o,max_repeats_per_artifact:1},{chat:t});return D(n)?.kind==="sound-effects-uncovered"?{ok:!1,message:"No existing indexed sound effects cover these beats. Generation is available as a fallback."}:await Xt(ft(n),t)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},eu=async(e,t,o)=>{if(!i)return{ok:!1,message:"Load or create a book first."};try{const n=Ke(await w("add_sequence_track",{book_id:i,kind:e,...t?.trim()?{name:t.trim()}:{}},{chat:o}));if(!n)throw new Error("The server returned an invalid sequence");return Ee(n),{ok:!0,message:`Added ${e} track`}}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},tu=async(e,t)=>{if(!i)return{ok:!1,message:"Load or create a book first."};try{const o=Ke(await w("remove_sequence_track",{book_id:i,track_id:e},{chat:t}));if(!o)throw new Error("The server returned an invalid sequence");return Ee(o),{ok:!0,message:"Removed empty track"}}catch(o){return{ok:!1,message:o instanceof Error?o.message:String(o)}}},Xa=async(e,t,o,n)=>{if(!i){Ue(s=>s?.key===e?{...s,setup:{status:"error",message:"Load or create a book first."}}:s);return}Ue(s=>s?.key===e?{...s,setup:{status:"loading"}}:s);const r=ec(o,t);if(!r){Ue(s=>s?.key===e?{...s,setup:{status:"needs-audio-track",message:"Create an empty, enabled soundtrack track before reviewing setup."}}:s);return}try{const s=ft(await w("plan_sequence_edit",{book_id:i,source_surface:"ui",actor:"videobook-user",expected_revision:await rr(o),edits:[{kind:"music_video_setup",audio_artifact_id:t,audio_track_id:r.trackId}]},{chat:n})),a=s.stages.find(v=>v.kind==="edit");if(!a)throw new Error("The soundtrack setup plan has no edit stage");const l=await w("preview_edit_intent",{book_id:i,intent:a.intent},{chat:n}),u=Jl(l);if(u)throw new Error(u);const d=iw(s,o,t);if(aw(o,t,d)){Ue(v=>v?.key===e?{...v,setup:{status:"applied",audioTrackId:r.trackId,timelineLimitFrame:d}}:v);return}const p={status:"ready",audioTrackId:r.trackId,timelineLimitFrame:d,operationCount:a.intent.operations.length,summary:lw(s),warnings:l.warnings.map(v=>v.message),plan:s,preview:l};Ue(v=>v?.key===e?{...v,setup:p}:v)}catch(s){const a=s instanceof Error?s.message:String(s);Ue(l=>l?.key===e?{...l,setup:{status:"error",message:a}}:l)}},Qa=async()=>{if(!i||!ve||ve.setup.status!=="ready")throw new Error("Review the soundtrack setup before applying it");const e=ve.key,t=ve.setup,o=t.plan.stages.find(n=>n.kind==="edit");if(!o)throw new Error("The soundtrack setup plan has no edit stage");Ue(n=>n?.key===e?{...n,setup:{status:"applying",audioTrackId:t.audioTrackId,timelineLimitFrame:t.timelineLimitFrame,operationCount:t.operationCount,summary:t.summary,warnings:t.warnings}}:n);try{const n=D(await w("commit_edit_intent",{book_id:i,intent:o.intent,preview_hash:t.preview.previewHash})),r=Ke(n?.sequence),s=_(n?.actionId);if(!r||!s)throw new Error("The server returned an invalid soundtrack commit");Ee(r),lo(s);const a=r.clips.find(l=>l.trackId===t.audioTrackId&&l.source.artifactId===ve.audioArtifactId);return a&&await wt.save({masterClipId:a.clipId,correction:null},r),Ue(l=>l?.key===e?{...l,setup:{status:"applied",audioTrackId:t.audioTrackId,timelineLimitFrame:t.timelineLimitFrame}}:l),{sequence:r,actionId:s,beforeRevision:o.intent.baseRevision}}catch(n){const r=n instanceof Error?n.message:String(n);throw Ue(s=>s?.key===e?{...s,setup:{status:"error",message:r}}:s),n}},Ya=async(e,t)=>{if(!i)throw new Error("Load or create a book first.");const n=ft(await w("plan_sequence_edit",{book_id:i,source_surface:"ui",actor:"videobook-user",expected_revision:await rr(t),edits:[e]})).stages.find(d=>d.kind==="edit");if(!n)throw new Error("The music-video plan has no edit stage");const r=await w("preview_edit_intent",{book_id:i,intent:n.intent}),s=Jl(r);if(s)throw new Error(s);const a=D(await w("commit_edit_intent",{book_id:i,intent:n.intent,preview_hash:r.previewHash})),l=Ke(a?.sequence),u=_(a?.actionId);if(!l||!u)throw new Error("The server returned an invalid music-video edit commit");return ye.current=performance.now(),Ee(l),lo(u),{sequence:l,actionId:u,beforeRevision:n.intent.baseRevision}},Za=async(e,t)=>await w("plan_music_video",{book_id:i,expected_revision:await rr(t),rhythm_revision:wt.rhythm.revision,options:e,source_surface:"ui",actor:"videobook-user"}),ei=async e=>{const t=e.plan.stages[0]?.intent;if(!t||e.uncovered.length)throw new Error("Review a complete draft before applying it");const o=D(await w("commit_music_video",{book_id:i,intent:t,preview_hash:e.preview.previewHash,rhythm_revision:e.rhythmRevision,sequence_content_revision:e.sequenceContentRevision})),n=Ke(o?.sequence),r=_(o?.actionId);if(!n||!r)throw new Error("The server returned an invalid draft commit");return ye.current=performance.now(),Ee(n),lo(r),{sequence:n,actionId:r,beforeRevision:t.baseRevision}},ti=async(e,t)=>{if(!i)throw new Error("Load or create a book first.");const o=D(await w("restore_edit_action",{book_id:i,target_revision:e,base_revision:t,actor:"videobook-user",source_surface:"ui"})),n=Ke(o?.sequence),r=_(o?.actionId);if(!n||!r)throw new Error("The server returned an invalid sequence restore");return ye.current=performance.now(),Ee(n),lo(r),{sequence:n,actionId:r,beforeRevision:t}},oi=async e=>{if(!i)throw new Error("Load or create a book first.");const t=Ke(await w("add_sequence_track",{book_id:i,kind:e,name:e==="audio"?"Master Soundtrack":"Music Video"}));if(!t)throw new Error("The server returned an invalid sequence");return ye.current=performance.now(),Ee(t),t},ni=m.useCallback(()=>{const e=nr();Ue(null),e()},[]),ou=m.useCallback(()=>{const e=nr();Er(null),e()},[]),ri=(e,t)=>{Er(o=>o?.key===e?{...o,state:t}:o)},si=async(e,t,o,n)=>{try{const r=await w("alive_captions",{book_id:i,asset_id:t,reanalyze:o},{chat:n});ri(e,{status:"ready",data:pg(r)})}catch(r){if(o)throw new Error($s(r),{cause:r});ri(e,{status:"error",message:$s(r)})}},ai=async(e,t)=>{try{await w("set_alive_captions",{book_id:i,asset_id:e,...gg(t)})}catch(o){throw new Error($s(o),{cause:o})}},nu=async(e,t,o)=>{await ai(e,t),await w("render_video",{book_id:i,asset_id:e,orientation:o,subtitles_enabled:!0,highlight_style:"alive"})},Hn=async(e,t,o,n,r)=>{if(!c)return await F(i,void 0,o,n),{ok:!0,message:kn(e,"Download queued")};const s=Kg(e,t,r??Mo("video",c.cells,Ge));let a;try{const l=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:s},{chat:n})),u=_(l?.id);if(!u)throw new Error("The server did not return the new notebook cell");if(a=u,o?.()===!1)return{ok:!0,message:"Download queued in the previous workspace."};Z(u,n),ae(n)}catch(l){return await F(i,c.id,o,n),{ok:!1,message:`Download queued in Library, but board placement failed: ${l instanceof Error?l.message:String(l)}`}}return await F(i,c.id,o,n),Gc({bookId:i,notebookId:c.id,cellId:a,address:Se(s.slot),artifactId:s.output_artifact_id}),{ok:!0,message:kn(e,`Download queued as ${W(s.slot)}`)}},ru=async(e,t)=>{if(!(!i||!c))try{const o=await w("download_video",{book_id:i,url:e}),n=await Hn(o,e,void 0,void 0,t);h(n.message,n.ok?"info":"error")}catch(o){h(o instanceof Error?o.message:String(o),"error")}},su=async(e,t)=>{let o;try{o=await Pt({bookId:e.bookId,notebookId:e.notebookId,cellId:e.run.actionCellId,address:e.actionAddress.slice(1),runId:e.run.runId,jobOperationId:e.run.jobId,intervalMs:wn,timeoutMs:hn,maxPollFailures:10}),o.kind==="failed"&&ne(e.run.actionCellId,o.message??`${e.actionAddress} failed`)}catch(n){const r=n instanceof Error?n.message:String(n);ne(e.run.actionCellId,r),o={kind:"failed",message:r}}finally{oe(e.run.actionCellId,!1)}if(o.kind==="failed"){M(t,()=>h(o.message??`${e.actionAddress} failed`,"error"));return}if(o.kind==="timeout"){M(t,()=>h(`${e.sourceAddress} is still splitting — check the Jobs screen`));return}o.kind!=="superseded"&&(Z(e.run.outputs.at(-1)?.outputCellId??null,t),M(t,()=>h(`Split ${e.sourceAddress} into ${e.outputAddresses.join(" and ")}`)))},au=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before splitting a video."};let n=null;T(!0);try{const r=await w("list_assets",{book_id:i,sort:"newest",limit:200,include_referenced:!0},{chat:o}),s=Lt(r),a=St(t,e.sourceReference),l=W(a.slot),u=dr(t,a),d=s.find(y=>y.artifactId===u)?.duration??ie(a.inputs?.durationSeconds),p=Vk({command:e,document:t,sourceDurationSeconds:d??Number.NaN}),v=W(p.actionCell.slot),S=p.outputs.map(y=>W(y.outputCell.slot));n=p.actionCell.id,Je(s),Ie(p.document,s,Ve),M(o,()=>en(p.createdCellIds)),ne(n,null),oe(n,!0),Z(p.outputs[0].outputCell.id,o),M(o,()=>h(`Splitting ${l} into ${p.outputs.length} chunks`));const A=await Gk({actor:"videobook-user",bookId:i,callTool:(y,R)=>w(y,R,{chat:o}),draft:p,...t.revision?{expectedRevision:t.revision}:{}});return ae(o),await F(i,t.id,void 0,o).catch(()=>{}),su({actionAddress:v,bookId:i,notebookId:t.id,outputAddresses:S,run:A,sourceAddress:l},o),{ok:!0,message:`Splitting ${l} into ${S.join(", ")}`}}catch(r){const s=r instanceof Error?r.message:String(r);return n&&oe(n,!1),await F(i,c.id,void 0,o).catch(()=>{}),M(o,()=>h(s,"error")),{ok:!1,message:s}}finally{T(!1)}},ii=async(e,t,o,n)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting a frame."};let r=null;T(!0);try{const s=St(t,e.sourceReference),a=W(s.slot),l=await Fk({actor:"videobook-user",bookId:i,callTool:(p,v)=>w(p,v,{chat:n}),command:e,document:t,...t.revision?{expectedRevision:t.revision}:{}});if(r=l.actionCellId,o?.()===!1)return{ok:!0,message:"Frame extraction queued in the previous workspace."};ae(n),ne(r,null),oe(r,!0),Z(l.outputCellId??r,n),M(n,()=>h(`Frame extraction queued for ${a}`));const u=await Pt({bookId:i,notebookId:t.id,cellId:r,address:Se(s.slot),runId:l.runId,jobOperationId:l.jobId,intervalMs:wn,timeoutMs:hn,maxPollFailures:fr});if(o?.()===!1)return{ok:!0,message:"Check the previous workspace for the accepted frame extraction."};if(u.kind==="failed")throw new Error(u.message??`Frame extraction for ${a} failed`);if(u.kind==="timeout")throw new Error("Frame extraction did not finish within five minutes");if(u.kind==="superseded")throw new Error(`Frame extraction for ${a} was superseded by a newer run`);return Z(l.outputCellId??r,n),{ok:!0,message:e.frameMode==="time"?`Extracted the frame at ${e.timestampSeconds??0}s of ${a}`:`Extracted the ${e.frameMode} frame of ${a}`}}catch(s){const a=s instanceof Error?s.message:String(s);return o?.()!==!1&&(r&&ne(r,a),M(n,()=>h(a,"error"))),{ok:!1,message:a}}finally{r&&o?.()!==!1&&oe(r,!1),T(!1)}},iu=async(e,t,o,n)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting audio."};let r=null;T(!0);try{const s=St(t,e.sourceReference),a=W(s.slot),l=await Lk({actor:"videobook-user",bookId:i,callTool:(d,p)=>w(d,p,{chat:n}),command:e,document:t,...t.revision?{expectedRevision:t.revision}:{}});if(r=l.actionCellId,o?.()===!1)return{ok:!0,message:"Audio extraction queued in the previous workspace."};ae(n),ne(r,null),oe(r,!0),Z(l.outputCellId??r,n),M(n,()=>h(`Audio extraction queued for ${a}`));const u=await Pt({bookId:i,notebookId:t.id,cellId:r,address:Se(s.slot),runId:l.runId,jobOperationId:l.jobId,intervalMs:wn,timeoutMs:hn,maxPollFailures:fr});if(o?.()===!1)return{ok:!0,message:"Check the previous workspace for the accepted audio extraction."};if(u.kind==="failed")throw new Error(u.message??`Audio extraction for ${a} failed`);if(u.kind==="timeout")throw new Error("Audio extraction did not finish within five minutes");if(u.kind==="superseded")throw new Error(`Audio extraction for ${a} was superseded by a newer run`);return Z(l.outputCellId??r,n),{ok:!0,message:`Extracted audio from ${a}`}}catch(s){const a=s instanceof Error?s.message:String(s);return o?.()!==!1&&(r&&ne(r,a),M(n,()=>h(a,"error"))),{ok:!1,message:a}}finally{r&&o?.()!==!1&&oe(r,!1),T(!1)}},li=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting audio."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");return St(n,e.sourceReference),L(o,!1,()=>le(null)),L(o,!1,()=>O(null)),await iu(e,n,t,o)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},ci=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting a frame."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");return St(n,e.sourceReference),L(o,!1,()=>le(null)),L(o,!1,()=>O(null)),await ii(e,n,t,o)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},di=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting a frame."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");const r=St(n,e.sourceReference),s=e.frameMode==="time"?`Extract the frame at ${e.timestampSeconds??0}s from ${W(r.slot)}`:`Extract the ${e.frameMode} frame from ${W(r.slot)}`;return L(o,!1,()=>le(null)),L(o,!0,()=>O({kind:"frame",command:e,expectations:[{address:W(r.slot),cellId:r.id}],notebookId:n.id,reason:"This request extracts a frame into a new image cell",summary:s})),pt("Frame extraction ready to apply")}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},cn=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before splitting a video."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");const r=St(n,e.sourceReference),s=dr(n,r),a=s?re.get(s):void 0,l=a?.duration??ie(r.inputs?.durationSeconds);if(!a?.mediaUrl)throw new Error(`${W(r.slot)} does not have playable video yet`);const u=gn.maximumRowCount*gn.columnCount,d=e.outputMode??"all",p=e.cutPointsSeconds.filter(R=>l===null||Math.abs(R-l)>.001),v=d==="all"?Qg({cutPointsSeconds:p,sourceDurationSeconds:l??Number.NaN}):yl({cutPointsSeconds:p,sourceDurationSeconds:l??Number.NaN}).slice(0,-1).map(R=>R.endSeconds),S={...e,cutPointsSeconds:v,outputMode:d,selectedChunkIndexes:e.selectedChunkIndexes??(d==="all"?[0]:e.selectedChunkIndexes??[0])},A=yl({cutPointsSeconds:v,sourceDurationSeconds:l??Number.NaN}).length,y=Yg(d,A);if(u-n.cells.length<y)throw new Error(`The notebook needs ${y} empty cells to split a video`);return L(o,!1,()=>le(null)),L(o,!0,()=>O({kind:"split",command:S,expectations:[{address:W(r.slot),cellId:r.id}],notebookId:n.id,reason:"This request creates and runs a Split Video workflow",sourceDurationSeconds:l??Number.NaN,summary:Ji({cutPointsSeconds:v,outputMode:d,selectedChunkIndexes:S.selectedChunkIndexes,sourceAddress:W(r.slot),sourceDurationSeconds:l??Number.NaN})})),pt("Video split ready to apply")}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},lu=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before generating media."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.isCurrent?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");let r=Ql({actions:Qe,cellId:xt(),command:e,document:n,fallbackSlot:Mo(e.cellType,n.cells,Ge),lastWorkSlot:Ge,...t?.preferredModel?{preferredModel:t.preferredModel}:{},...t?.routedParams?{routedParams:t.routedParams}:{}});const s=r.sourceCellIds.flatMap(l=>{const u=n.cells.find(d=>d.id===l);return u?[u]:[]});if(r=tr(r,mk(e.prompt,se,s)),r.cell.type==="generate_audio"&&r.action.controls.some(l=>l.name==="voice_id")&&typeof sl(r).voice_id!="string"){const l=pk(Bn.voices,gk());l&&(r=xs(r,"voice_id",l))}kk(r,n);const a=r.sourceCellIds.length>0?` from ${r.sourceCellIds.flatMap(l=>{const u=n.cells.find(d=>d.id===l);return u?[W(u.slot)]:[]}).join(", ")}`:"";return L(o,!1,()=>le(null)),L(o,!0,()=>O({kind:"generation",draft:r,notebookId:n.id,preview:null,previewError:null,previewLoading:!0,previewStale:!1,expectations:[...r.sourceCellIds.flatMap(l=>{const u=n.cells.find(d=>d.id===l);return u?[{address:W(u.slot),cellId:u.id}]:[]}),{address:W(r.cell.slot),cellId:null}],reason:t?.reason??"Generation can incur provider spend and sends the prompt and required references",summary:`Generate ${e.mediaKind} as ${W(r.cell.slot)}${a}`})),jt(r,n,o),Hl(`Generation ready to apply as ${W(r.cell.slot)}`)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},rs=e=>e==="completed"||e==="failed"||e==="cancelled"||e==="interrupted"||e==="awaiting-approval",ui=async(e,t,o,n)=>{Ot("videobook.active-chain",JSON.stringify({bookId:e,chainId:t.chainId}));const r=Date.now()+5*6e4;let s=t;for(;Date.now()<r;){const a=Ls(await w("chain",{action:"status",book_id:e,chain_id:t.chainId},{background:!0,chat:n}));if(o?.()===!1)throw new Error("Workspace changed. Check the previous project for the accepted action.");if(!a)break;s=a;const l=a.steps.find(u=>u.status==="running");if(l&&M(n,()=>h(`${l.tool.replaceAll("_"," ")}…`)),rs(a.status))return a.status!=="awaiting-approval"&&Ot("videobook.active-chain",""),a;await new Promise(u=>window.setTimeout(u,250))}throw new Error(s.error??"Chain timed out")},fi=(e,t)=>{const n=e.steps.find(s=>s.id===e.awaitingStepId)?.review;if(!n)return{ok:!1,message:"The chain is waiting for approval but sent no review."};const r=e.steps.filter(s=>s.status==="pending").length;return L(t,!0,()=>O({kind:"chain-step",chainId:e.chainId,review:n,remaining:r})),M(t,()=>h(n.reason)),{ok:!0,message:n.reason,nextInput:"/apply",selectInput:!1}},cu=async(e,t)=>{if(!i)return{ok:!1,message:"Load or create a book first."};L(t,!1,()=>O(null)),T(!0);try{const o=Ls(await w("chain",{action:"approve",book_id:i,chain_id:e.chainId,step_id:e.review.stepId,actor:"chat"},{chat:t}));if(!o)throw new Error("The server did not return the chain run");const n=rs(o.status)?o:await ui(i,o,void 0,t);if(n.status==="awaiting-approval")return fi(n,t);if(await F(i,c?.id,void 0,t),n.status!=="completed")throw new Error(n.error??`Chain ${n.status}`);const r="Chain complete";return M(t,()=>h(r)),{ok:!0,message:r}}catch(o){const n=o instanceof Error?o.message:String(o);return M(t,()=>h(n,"error")),{ok:!1,message:n}}finally{T(!1)}},mi=async(e,t,o)=>{if(!i)return{ok:!1,message:"Load or create a book first."};L(o,!1,()=>le(null)),T(!0);let n=!1;try{const r=await w("chat",{book_id:i,action_plan:e},{chat:o});if(n=!0,t?.()===!1)return{ok:!1,message:"Workspace changed. Check the previous project for the accepted action."};L(o,!1,()=>O(null));const s=Ls(r),a=s&&!rs(s.status)?await ui(i,s,t,o):s;if(a?.status==="awaiting-approval")return fi(a,o);const l=a;if(a&&a.status!=="completed")throw new Error(a.error??`Chain ${a.status}`);if(t?.()===!1)return{ok:!0,message:"Action accepted in the previous workspace."};if(hl(r)){const A=await Hn(r,Kl(e.prompt),t,o);return t?.()===!1?A:(M(o,()=>h(A.message,A.ok?"info":"error")),A.ok?A:{...A,nextInput:"",selectInput:!1})}const u=c?Il(e.tool,r,c.cells,Ge):[];if(c&&u.length>0){const A=[];let y=null;for(const q of u){if(t?.()===!1)return{ok:!0,message:"Action accepted in the previous workspace."};const V=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:q},{chat:o})),X=_(V?.id);if(!X)throw new Error("The server did not return the new notebook cell");y??=X,A.push(W(q.slot))}if(t?.()===!1)return{ok:!0,message:"Action accepted in the previous workspace."};Z(y,o),await F(i,c.id,t,o),ae(o);const R=`Created ${A.join(" and ")}`;return t?.()!==!1&&M(o,()=>h(R)),{ok:!0,message:R}}const d=D(r),p=_(d?.cell_id),v=await F(i,c?.id,t,o);if(t?.()===!1)return{ok:!0,message:"Action accepted in the previous workspace."};p&&Z(p,o),ir(c,v)&&ae(o);const S=l?e.message||"Chain complete":kn(r,e.message||"Action applied");return M(o,()=>h(S)),{ok:!0,message:S}}catch(r){const s=r instanceof Error?r.message:String(r);if(t?.()===!1)return{ok:!1,message:s};const a=n?`Action completed, but its notebook result could not be shown: ${s}`:s;return n&&await F(i,c?.id,t,o).catch(()=>{}),M(o,()=>h(a,"error")),{ok:!1,message:a,nextInput:n?"":"/apply",selectInput:!n}}finally{T(!1)}},du=async(e,t,o)=>{if(!i||!c||e.tool!=="post"&&e.routedTool!=="post")return null;const r=(_(e.params.asset_id)?.trim()??"").replace(/^@/,""),s=se.find(y=>y.artifactId===r||y.cellAddress.toLowerCase()===r.toLowerCase()),a=s?.artifactId??r,l=re.get(a)??s;if(!a||l?.type!=="video"&&l?.type!=="final")return null;const u=c.posts?.find(y=>y.id===e.params.post_cell_id),d=bk(c,u?.definition.source?.artifactId??a),p=[...B.map(y=>({reference:y.artifactId,type:y.type})),...se.map(y=>({reference:y.cellAddress,type:y.type}))],v=await Promise.all(d.steps.map(async y=>{const R=await w("list_cell_generations",{book_id:i,notebook_id:c.id,cell_id:y.outputCellId??y.producerCellId,limit:20},{background:!0,chat:o}).catch(()=>null),q=D(R)?.attempts,V=Array.isArray(q)?q:[],X=wk(hk({attempts:V,outputArtifactId:y.outputArtifactId,outputAssetPrompt:y.outputArtifactId?re.get(y.outputArtifactId)?.prompt??null:null,producerResolvedPrompt:y.producerResolvedPrompt,producerPrompt:y.producerPrompt}),p),P=y.sourceArtifactIds.flatMap(H=>{const te=re.get(H);if(te?.type!=="image")return[];const de=se.find(pe=>pe.artifactId===H);return[{assetId:H,label:de?`@${de.cellAddress}`:te.id,mediaUrl:te.mediaUrl,thumbnailUrl:te.thumbnailUrl}]}),N=vk({attempts:V,outputArtifactId:y.outputArtifactId,producerTool:y.producerTool,producerModel:y.producerModel,producerProvider:y.producerProvider,actions:Qe});return{id:y.id,prompt:X,model:N,images:P}})),S=await Promise.all(d.upstreamArtifactIds.filter(y=>{const R=re.get(y);return R?.origin==="download"&&(R.type==="video"||R.type==="final")}).map(async y=>{const R=await w("read_asset_metadata",{asset_id:y,name:"original",book_id:i},{background:!0,chat:o}).catch(()=>null),q=D(R);return q?yk(y,q):null})),A=Ik(S.filter(y=>y!==null));return Ck({steps:v,credits:A},t)},uu=async e=>{const t=e.definition.source?.snapshotArtifactId;if(!t)return;const o={kind:"chat-action-plan",planId:xt(),bookId:i,prompt:`Post ${e.address} to X`,routedTool:"post",tool:"post",params:{book_id:i,asset_id:t,post_cell_id:e.id,platform:"x",text:e.definition.caption},message:"Review your X publication",summary:"Publish the saved clip to X",effect:"mutation",confirmation:{required:!0,reason:"Publishes this clip to X"}};await Kn(o,o.prompt),me(!0)},ss=(e,t)=>{if(g.state!=="ready"||!i||!c)return{ok:!1,message:"Open a connected notebook before making a cold open."};const o=e?.replace(/^@/,""),n=o?se.find(l=>l.artifactId===o||l.cellAddress.toLowerCase()===o.toLowerCase()):null,r=n?.artifactId??o??$?.outputArtifactId,s=r?re.get(r):null;if(!s||!["video","final"].includes(s.type)||!s.mediaUrl)return{ok:!1,message:"Select a playable video or use /edit-cold-open @a1."};const a=s.mediaUrl;return L(t,!1,()=>le(null)),L(t,!1,()=>Te(null)),L(t,!0,()=>O({kind:"cold-open",review:{bookId:i,notebookId:c.id,assetId:s.artifactId,label:n?`@${n.cellAddress}`:s.label??s.id,mediaUrl:a,requestId:xt(),suggestion:null}})),me(!0),pt("Cold-open review opened")},dn=c?.posts??[],as=(e,t)=>w(e,t,{background:!0}),ut=e=>O(t=>t?.kind==="post-delivery"?{...t,review:{...t.review,...e}}:t),is=async()=>{try{ut({connection:await Wp(as)})}catch(e){ut({connection:{connected:!1,pending:!1,hasCredentials:!0,error:e instanceof Error?e.message:String(e)}})}},fu=async()=>{try{const e=await Sk(as);O(t=>t?.kind==="post-delivery"?{...t,review:xk(t.review,e)}:t)}catch(e){ut({icloud:{available:!1,root:"",shared:null,role:null,reason:e instanceof Error?e.message:String(e)}})}},mu=async()=>{const e=window.open("about:blank","_blank");ut({connecting:!0});try{const t=await zp(w);e?e.location.href=t:window.open(t,"_blank","noopener,noreferrer");const o=Q.current.bookId,n=await Bp(as,rt,()=>Q.current.bookId===o);ut({connection:n,connecting:!1})}catch(t){e?.close(),ut({connecting:!1,connection:{connected:!1,pending:!1,hasCredentials:!0,error:t instanceof Error?t.message:String(t)}})}},ls=(e,t,o)=>{if(g.state!=="ready"||!i||!c)return{ok:!1,message:"Open a connected notebook before delivering a Post."};const n=ul(dn,c.cells,e,$?.id??null),r=t==="dropbox"?"/upload-post-to-dropbox @b1":"/save-post-to-icloud @b1";return n?us(n,t,o):{ok:!1,message:e?.trim()?`${e.trim()} is not a Post or a clip. Select one or use ${r}.`:`Select a Post cell or use ${r}.`}},cs=async(e,t,o)=>{const n=e?.trim(),r=n&&g.state==="ready"&&i&&c&&!ul(dn,c.cells,n,null)?ak(c.cells,n):null;if(!r||!i||!c)return ls(e,t,o);const s=ik(dn,r.id);if(s)return us(s,t,o);try{const a=await w("create_post",{book_id:i,notebook_id:c.id,source_cell_id:r.id});return await F(i,c.id),us(a,t,o)}catch(a){return{ok:!1,message:a instanceof Error?a.message:String(a)}}},ds=async(e,t,o,n,r)=>{const s=xt(),a=l=>l?.kind==="post-delivery"&&l.review.postId===t&&l.review.copy.drafting?.requestId===s;O(l=>l?.kind==="post-delivery"&&l.review.postId===t?{...l,review:{...l.review,copy:{...l.review.copy,drafting:{requestId:s,language:n},error:null}}}:l);try{const l=Ag(await w("draft_post_copy",_g(e,t,o,n,r)));O(u=>a(u)&&u?.kind==="post-delivery"?{...u,review:{...u.review,copy:Rg(u.review.copy,n,l,r)}}:u)}catch(l){const u=l instanceof Error?l.message:String(l);O(d=>a(d)&&d?.kind==="post-delivery"?{...d,review:{...d.review,copy:{...d.review.copy,drafting:null,error:u}}}:d)}},pu=(e,t,o)=>{const n={...t.copy,language:o};ut({copy:n}),dl(n,o,js(e))&&ds(t.bookId,e.id,n,o,null)},gu=(e,t)=>{js(e)||t.copy.drafting||ds(t.bookId,e.id,t.copy,t.copy.language,t.copy.prompt.trim()||null)},us=(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a connected notebook before delivering a Post."};const n=co?.name??"book",r=Lg(e);return L(o,!1,()=>le(null)),L(o,!1,()=>Te(null)),L(o,!0,()=>O({kind:"post-delivery",review:{bookId:i,notebookId:c.id,postId:e.id,entry:t,destination:t,pinnedDestination:!1,copy:r,icloudFolder:Dg(e,n),dropboxFolder:Fg(e,n),connection:null,connecting:!1,icloud:null,receipt:null,sync:null}})),me(!0),fu(),t==="dropbox"&&is(),dl(r,r.language,js(e))&&ds(i,e.id,r,r.language,null),pt(t==="dropbox"?"Dropbox upload review opened":"Save to iPhone review opened")},ku=e=>{ut({destination:e,pinnedDestination:!0}),e==="dropbox"&&is()},Kn=async(e,t,o,n)=>{const r=d=>{const p=_(d);return p?sr(Ns(p.startsWith("@")?p:`@${p}`,se))[0]??null:null};if(e.tool==="prepare_cold_open"||e.tool==="edit_cold_open")return ss(_(e.params.asset_id)??void 0,n);if(e.tool==="upload_post_to_dropbox"||e.tool==="save_post_to_icloud")return cs(_(e.params.post_cell_id)??void 0,e.tool==="upload_post_to_dropbox"?"dropbox":"icloud",n);if(e.tool==="show_media_fullscreen"){const d=Cg(e.params,c?.cells??[],B);return d.ok?o?.()===!1||n?.isCurrent()===!1?{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."}:(L(n,!1,()=>O(null)),L(n,!1,()=>le(null)),Vn(d.cell,d.asset),{ok:!0,message:`Opened ${d.address} fullscreen`}):d}if(e.tool==="apply_watermark"||e.routedTool==="apply_watermark"){const d=_(e.params.asset_id)?.replace(/^@/,""),v=(d?se.find(Oe=>Oe.artifactId===d||Oe.cellAddress.toLowerCase()===d.toLowerCase()):void 0)?.artifactId??d,S=kl(v,$,B,new Map(se.map(Oe=>[Oe.artifactId,Oe.cellAddress])));if(!S.ok)return{ok:!1,message:S.message};const A=ie(e.params.qr_start_seconds),y=ie(e.params.qr_end_seconds),R=ie(e.params.handle_start_seconds),q=ie(e.params.handle_end_seconds),V=ie(e.params.qr_opacity),X=ie(e.params.handle_opacity),P=ie(e.params.handle_vertical_percent),N=ie(e.params.handle_padding),H=ie(e.params.handle_padding_y),te=ie(e.params.handle_rounding),de=ie(e.params.fade_seconds),pe=e.params.position,He=e.params.handle_position,be=e.params.include_platform_icon;return Ba(S.artifactId,S.label,{...Sg(e.params.platform)?{platform:e.params.platform}:{},..._(e.params.handle)?{handle:_(e.params.handle)??void 0}:{},..._(e.params.url)?{url:_(e.params.url)??void 0}:{},...typeof e.params.include_qr=="boolean"?{includeQr:e.params.include_qr}:{},...typeof e.params.include_handle=="boolean"?{includeHandle:e.params.include_handle}:{},...Wk(pe)?{position:pe}:{},...P!==null?{handleVerticalPercent:_l(P)}:{},...Uk(He)?{handlePlacement:He}:{},...typeof be=="boolean"?{includePlatformIcon:be}:{},...typeof e.params.include_handle_border=="boolean"?{includeHandleBorder:e.params.include_handle_border}:{},...N!==null?{handlePadding:cr(N)}:{},...H!==null?{handlePaddingY:cr(H)}:{},...te!==null?{handleRounding:Al(te)}:{},...V!==null?{qrOpacity:lr(V)}:{},...X!==null?{handleOpacity:lr(X)}:{},...A!==null&&A>=0?{qrStartSeconds:A}:{},...y!==null&&y>=0?{qrEndSeconds:y}:{},...R!==null&&R>=0?{handleStartSeconds:R}:{},...q!==null&&q>=0?{handleEndSeconds:q}:{},...de!==null?{fadeSeconds:El(de)}:{},...typeof e.params.save_default=="boolean"?{saveDefault:e.params.save_default}:{}},n),pt(`Watermark review ready for ${S.label}`)}if(e.tool==="transcribe"||e.routedTool==="transcribe")return sn({assetRef:_(e.params.asset_id)??void 0,languageCode:_(e.params.language_code)??"",diarize:typeof e.params.diarize=="boolean"?e.params.diarize:!0,tagAudioEvents:typeof e.params.tag_audio_events=="boolean"?e.params.tag_audio_events:!0,chat:n});if(e.tool==="extract_audio"){const d=r(e.params.asset_id);return d?await li({sourceReference:d},o,n):{ok:!1,message:"The chat model did not select a video source."}}if(e.tool==="extract_frame"&&(e.params.frame==="first"||e.params.frame==="last")){const d=r(e.params.asset_id);if(!d)return{ok:!1,message:"The chat model did not select a video source."};const p={frameMode:e.params.frame,sourceReference:d};return e.confirmation.required===!1?await ci(p,o,n):await di(p,o,n)}if(e.tool==="extract_frame"){const d=r(e.params.asset_id),p=ie(e.params.timestamp);if(!d||p===null||p<0)return{ok:!1,message:"The chat model did not select a valid video source and timestamp."};const v={frameMode:"time",sourceReference:d,timestampSeconds:p};return e.confirmation.required===!1?await ci(v,o,n):await di(v,o,n)}if(e.tool==="split_video"){const d=r(e.params.asset_id),p=ie(e.params.chunk_a_end);return!d||!p||p<=0?{ok:!1,message:"The chat model did not select a valid split source and time."}:await cn({sourceReference:d,cutPointsSeconds:[p]},o,n)}if(e.tool==="split_video_by_durations"&&e.params.destination===void 0){const d=r(e.params.asset_id),v=(Array.isArray(e.params.target_secs)?e.params.target_secs:[7]).map(ie);if(v.some(S=>S===null||S<=0))return{ok:!1,message:"The chat model did not select valid split durations."};if(d)return await cn({sourceReference:d,cutPointsSeconds:bl(v)},o,n)}if(e.effect==="generation"){const d=xg(e.tool,e.routedTool,Qe),p=_(e.params.prompt)??t,v=Ns(p,se),S=Eg(e.params).map(q=>Ns(`@${q}`,se)).join(" "),A=sr(S),y=sr(v),R={cellType:d,mediaKind:Gs(d),prompt:p,sourceReferences:A.length>0?A:y.length>0?y:sr(t)};return await lu(R,{isCurrent:o,..._(e.params.model)?{preferredModel:_(e.params.model)}:{},reason:e.confirmation.reason,routedParams:e.params},n)}if(e.confirmation.required===!1)return await mi(e,o,n);const a=e.tool==="post"||e.routedTool==="post"?await Ka():null,l=await du(e,Zn(a??$o.status),n),u=l?{...e,params:pn(e.params,eo(l))}:e;return o?.()===!1?{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."}:(L(n,!1,()=>le(null)),L(n,!0,()=>O({kind:"routed",plan:u,xPostReview:l})),pt("Action preview ready"))},bu=(e,t)=>{const o=Ss({...t,cells:[e.cell],edges:[]},B,Ve)[0];if(!o)return;const n=new Date().toISOString();ht(r=>r.some(s=>s.id===o.id)?r.map(s=>s.id===o.id?{...o,data:{...o.data,status:"queued",statusStartedAt:n}}:s):[...r,{...o,data:{...o.data,status:"queued",statusStartedAt:n}}])},wu=async(e,t=null,o)=>{const n=t?{...e,draft:tr(e.draft,t)}:e,r=t?`/apply ${t}`:"/apply ";if(!n.draft.cell.prompt?.trim())return{ok:!1,message:"Enter a generation prompt before applying.",nextInput:r,selectInput:!1};if(!i||!c||c.id!==n.notebookId)return{ok:!1,message:"The generation draft belongs to another notebook."};let s;try{const A=ge(await w("get_notebook",{book_id:i,notebook_id:n.notebookId},{chat:o}));if(!A)throw new Error("The server returned an invalid notebook");s=A}catch(A){return{ok:!1,message:A instanceof Error?A.message:String(A),nextInput:r,selectInput:!1}}if(Pl(s,n.expectations))return L(o,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."};if(!_t)return{ok:!1,message:"Offline: cloud generation is unavailable.",nextInput:r,selectInput:!1};M(o,()=>O(A=>A?.kind==="generation"&&A.draft.cell.id===n.draft.cell.id?{...A,draft:n.draft,previewError:null,previewLoading:!0,previewStale:!1}:A));let a;try{$t.cancel(),ho.current+=1,a=await Xr(n.draft,s,o)}catch(A){const y=A instanceof Error?A.message:String(A);return M(o,()=>O(R=>R?.kind==="generation"&&R.draft.cell.id===n.draft.cell.id?{...R,draft:n.draft,previewError:y,previewLoading:!1,previewStale:!1}:R)),{ok:!1,message:y,nextInput:r,selectInput:!1}}M(o,()=>O(A=>A?.kind==="generation"&&A.draft.cell.id===n.draft.cell.id?{...A,draft:n.draft,preview:a,previewError:null,previewLoading:!1,previewStale:!1}:A));const l=Ok(a);if(l)return{ok:!1,message:l,nextInput:r,selectInput:!1};const u="videobook.cloud-generation-consent";if(window.localStorage.getItem(u)!=="accepted"){if(!window.confirm(`Cloud generation disclosure
|
|
31
|
+
This creates a new forward revision.`))){T(!0);try{const t=D(await w("get_edit_action",{book_id:i,action_id:qr})),o=_(t?.baseRevision);if(!o)throw new Error("The edit audit has no base revision");const n=D(await w("restore_edit_action",{book_id:i,target_revision:o,base_revision:J?.revision??_(t?.committedRevision)??"",actor:"videobook-user",source_surface:"ui"}));co(_(n?.actionId)??""),await F(i,c?.id),h("Restored the previous sequence state as a forward revision")}catch(t){h(t instanceof Error?t.message:String(t),"error")}finally{T(!1)}}},Zd=async(e,t)=>{if(!i||!c||!J)return{ok:!1,message:"Open a notebook sequence first."};const o=J.captions.slice(0,20).map(n=>({beat_id:n.cueId,text:n.text,timeline_start_frame:n.timelineStartFrame,duration_frames:n.durationFrames}));if(o.length===0)return{ok:!1,message:"Add captions first so narration beats have exact timing."};try{const n=await w("plan_notebook_rough_cut",{book_id:i,notebook_id:c.id,source_surface:e,actor:"videobook-user",beats:o,min_shot_frames:30,max_shot_frames:120,max_repeats_per_artifact:1},{chat:t}),r=D(n);return r?.kind==="rough-cut-uncovered"?{ok:!1,message:`No existing indexed coverage for ${Array.isArray(r.uncoveredBeats)?r.uncoveredBeats.length:o.length} narration beats.`}:await Xt(ft(n),t)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},eu=async(e,t)=>{if(!i||!J)return{ok:!1,message:"Open a sequence first."};const o=J.captions.slice(0,20).map(n=>({beat_id:n.cueId,text:n.text,timeline_start_frame:n.timelineStartFrame,duration_frames:n.durationFrames}));if(o.length===0)return{ok:!1,message:"Add captions first so sound suggestions have exact timing."};try{const n=await w("plan_sequence_sound_effects",{book_id:i,source_surface:e,actor:"videobook-user",moments:o,max_repeats_per_artifact:1},{chat:t});return D(n)?.kind==="sound-effects-uncovered"?{ok:!1,message:"No existing indexed sound effects cover these beats. Generation is available as a fallback."}:await Xt(ft(n),t)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},tu=async(e,t,o)=>{if(!i)return{ok:!1,message:"Load or create a book first."};try{const n=Ke(await w("add_sequence_track",{book_id:i,kind:e,...t?.trim()?{name:t.trim()}:{}},{chat:o}));if(!n)throw new Error("The server returned an invalid sequence");return Ee(n),{ok:!0,message:`Added ${e} track`}}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},ou=async(e,t)=>{if(!i)return{ok:!1,message:"Load or create a book first."};try{const o=Ke(await w("remove_sequence_track",{book_id:i,track_id:e},{chat:t}));if(!o)throw new Error("The server returned an invalid sequence");return Ee(o),{ok:!0,message:"Removed empty track"}}catch(o){return{ok:!1,message:o instanceof Error?o.message:String(o)}}},Xa=async(e,t,o,n)=>{if(!i){Ue(s=>s?.key===e?{...s,setup:{status:"error",message:"Load or create a book first."}}:s);return}Ue(s=>s?.key===e?{...s,setup:{status:"loading"}}:s);const r=ec(o,t);if(!r){Ue(s=>s?.key===e?{...s,setup:{status:"needs-audio-track",message:"Create an empty, enabled soundtrack track before reviewing setup."}}:s);return}try{const s=ft(await w("plan_sequence_edit",{book_id:i,source_surface:"ui",actor:"videobook-user",expected_revision:await rr(o),edits:[{kind:"music_video_setup",audio_artifact_id:t,audio_track_id:r.trackId}]},{chat:n})),a=s.stages.find(v=>v.kind==="edit");if(!a)throw new Error("The soundtrack setup plan has no edit stage");const l=await w("preview_edit_intent",{book_id:i,intent:a.intent},{chat:n}),u=Jl(l);if(u)throw new Error(u);const d=dw(s,o,t);if(cw(o,t,d)){Ue(v=>v?.key===e?{...v,setup:{status:"applied",audioTrackId:r.trackId,timelineLimitFrame:d}}:v);return}const p={status:"ready",audioTrackId:r.trackId,timelineLimitFrame:d,operationCount:a.intent.operations.length,summary:uw(s),warnings:l.warnings.map(v=>v.message),plan:s,preview:l};Ue(v=>v?.key===e?{...v,setup:p}:v)}catch(s){const a=s instanceof Error?s.message:String(s);Ue(l=>l?.key===e?{...l,setup:{status:"error",message:a}}:l)}},Qa=async()=>{if(!i||!ve||ve.setup.status!=="ready")throw new Error("Review the soundtrack setup before applying it");const e=ve.key,t=ve.setup,o=t.plan.stages.find(n=>n.kind==="edit");if(!o)throw new Error("The soundtrack setup plan has no edit stage");Ue(n=>n?.key===e?{...n,setup:{status:"applying",audioTrackId:t.audioTrackId,timelineLimitFrame:t.timelineLimitFrame,operationCount:t.operationCount,summary:t.summary,warnings:t.warnings}}:n);try{const n=D(await w("commit_edit_intent",{book_id:i,intent:o.intent,preview_hash:t.preview.previewHash})),r=Ke(n?.sequence),s=_(n?.actionId);if(!r||!s)throw new Error("The server returned an invalid soundtrack commit");Ee(r),co(s);const a=r.clips.find(l=>l.trackId===t.audioTrackId&&l.source.artifactId===ve.audioArtifactId);return a&&await wt.save({masterClipId:a.clipId,correction:null},r),Ue(l=>l?.key===e?{...l,setup:{status:"applied",audioTrackId:t.audioTrackId,timelineLimitFrame:t.timelineLimitFrame}}:l),{sequence:r,actionId:s,beforeRevision:o.intent.baseRevision}}catch(n){const r=n instanceof Error?n.message:String(n);throw Ue(s=>s?.key===e?{...s,setup:{status:"error",message:r}}:s),n}},Ya=async(e,t)=>{if(!i)throw new Error("Load or create a book first.");const n=ft(await w("plan_sequence_edit",{book_id:i,source_surface:"ui",actor:"videobook-user",expected_revision:await rr(t),edits:[e]})).stages.find(d=>d.kind==="edit");if(!n)throw new Error("The music-video plan has no edit stage");const r=await w("preview_edit_intent",{book_id:i,intent:n.intent}),s=Jl(r);if(s)throw new Error(s);const a=D(await w("commit_edit_intent",{book_id:i,intent:n.intent,preview_hash:r.previewHash})),l=Ke(a?.sequence),u=_(a?.actionId);if(!l||!u)throw new Error("The server returned an invalid music-video edit commit");return ye.current=performance.now(),Ee(l),co(u),{sequence:l,actionId:u,beforeRevision:n.intent.baseRevision}},Za=async(e,t)=>await w("plan_music_video",{book_id:i,expected_revision:await rr(t),rhythm_revision:wt.rhythm.revision,options:e,source_surface:"ui",actor:"videobook-user"}),ei=async e=>{const t=e.plan.stages[0]?.intent;if(!t||e.uncovered.length)throw new Error("Review a complete draft before applying it");const o=D(await w("commit_music_video",{book_id:i,intent:t,preview_hash:e.preview.previewHash,rhythm_revision:e.rhythmRevision,sequence_content_revision:e.sequenceContentRevision})),n=Ke(o?.sequence),r=_(o?.actionId);if(!n||!r)throw new Error("The server returned an invalid draft commit");return ye.current=performance.now(),Ee(n),co(r),{sequence:n,actionId:r,beforeRevision:t.baseRevision}},ti=async(e,t)=>{if(!i)throw new Error("Load or create a book first.");const o=D(await w("restore_edit_action",{book_id:i,target_revision:e,base_revision:t,actor:"videobook-user",source_surface:"ui"})),n=Ke(o?.sequence),r=_(o?.actionId);if(!n||!r)throw new Error("The server returned an invalid sequence restore");return ye.current=performance.now(),Ee(n),co(r),{sequence:n,actionId:r,beforeRevision:t}},oi=async e=>{if(!i)throw new Error("Load or create a book first.");const t=Ke(await w("add_sequence_track",{book_id:i,kind:e,name:e==="audio"?"Master Soundtrack":"Music Video"}));if(!t)throw new Error("The server returned an invalid sequence");return ye.current=performance.now(),Ee(t),t},ni=m.useCallback(()=>{const e=nr();Ue(null),e()},[]),nu=m.useCallback(()=>{const e=nr();Er(null),e()},[]),ri=(e,t)=>{Er(o=>o?.key===e?{...o,state:t}:o)},si=async(e,t,o,n)=>{try{const r=await w("alive_captions",{book_id:i,asset_id:t,reanalyze:o},{chat:n});ri(e,{status:"ready",data:bg(r)})}catch(r){if(o)throw new Error($s(r),{cause:r});ri(e,{status:"error",message:$s(r)})}},ai=async(e,t)=>{try{await w("set_alive_captions",{book_id:i,asset_id:e,...wg(t)})}catch(o){throw new Error($s(o),{cause:o})}},ru=async(e,t,o)=>{await ai(e,t),await w("render_video",{book_id:i,asset_id:e,orientation:o,subtitles_enabled:!0,highlight_style:"alive"})},Bn=async(e,t,o,n,r)=>{if(!c)return await F(i,void 0,o,n),{ok:!0,message:kn(e,"Download queued")};const s=Qg(e,t,r??Mo("video",c.cells,Ge));let a;try{const l=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:s},{chat:n})),u=_(l?.id);if(!u)throw new Error("The server did not return the new notebook cell");if(a=u,o?.()===!1)return{ok:!0,message:"Download queued in the previous workspace."};Z(u,n),ae(n)}catch(l){return await F(i,c.id,o,n),{ok:!1,message:`Download queued in Library, but board placement failed: ${l instanceof Error?l.message:String(l)}`}}return await F(i,c.id,o,n),Gc({bookId:i,notebookId:c.id,cellId:a,address:Se(s.slot),artifactId:s.output_artifact_id}),{ok:!0,message:kn(e,`Download queued as ${W(s.slot)}`)}},su=async(e,t)=>{if(!(!i||!c))try{const o=await w("download_video",{book_id:i,url:e}),n=await Bn(o,e,void 0,void 0,t);h(n.message,n.ok?"info":"error")}catch(o){h(o instanceof Error?o.message:String(o),"error")}},au=async(e,t)=>{let o;try{o=await Pt({bookId:e.bookId,notebookId:e.notebookId,cellId:e.run.actionCellId,address:e.actionAddress.slice(1),runId:e.run.runId,jobOperationId:e.run.jobId,intervalMs:wn,timeoutMs:hn,maxPollFailures:10}),o.kind==="failed"&&ne(e.run.actionCellId,o.message??`${e.actionAddress} failed`)}catch(n){const r=n instanceof Error?n.message:String(n);ne(e.run.actionCellId,r),o={kind:"failed",message:r}}finally{oe(e.run.actionCellId,!1)}if(o.kind==="failed"){M(t,()=>h(o.message??`${e.actionAddress} failed`,"error"));return}if(o.kind==="timeout"){M(t,()=>h(`${e.sourceAddress} is still splitting — check the Jobs screen`));return}o.kind!=="superseded"&&(Z(e.run.outputs.at(-1)?.outputCellId??null,t),M(t,()=>h(`Split ${e.sourceAddress} into ${e.outputAddresses.join(" and ")}`)))},iu=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before splitting a video."};let n=null;T(!0);try{const r=await w("list_assets",{book_id:i,sort:"newest",limit:200,include_referenced:!0},{chat:o}),s=Lt(r),a=St(t,e.sourceReference),l=W(a.slot),u=dr(t,a),d=s.find(y=>y.artifactId===u)?.duration??ie(a.inputs?.durationSeconds),p=Wk({command:e,document:t,sourceDurationSeconds:d??Number.NaN}),v=W(p.actionCell.slot),S=p.outputs.map(y=>W(y.outputCell.slot));n=p.actionCell.id,Je(s),Ie(p.document,s,Ve),M(o,()=>en(p.createdCellIds)),ne(n,null),oe(n,!0),Z(p.outputs[0].outputCell.id,o),M(o,()=>h(`Splitting ${l} into ${p.outputs.length} chunks`));const A=await zk({actor:"videobook-user",bookId:i,callTool:(y,R)=>w(y,R,{chat:o}),draft:p,...t.revision?{expectedRevision:t.revision}:{}});return ae(o),await F(i,t.id,void 0,o).catch(()=>{}),au({actionAddress:v,bookId:i,notebookId:t.id,outputAddresses:S,run:A,sourceAddress:l},o),{ok:!0,message:`Splitting ${l} into ${S.join(", ")}`}}catch(r){const s=r instanceof Error?r.message:String(r);return n&&oe(n,!1),await F(i,c.id,void 0,o).catch(()=>{}),M(o,()=>h(s,"error")),{ok:!1,message:s}}finally{T(!1)}},ii=async(e,t,o,n)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting a frame."};let r=null;T(!0);try{const s=St(t,e.sourceReference),a=W(s.slot),l=await Vk({actor:"videobook-user",bookId:i,callTool:(p,v)=>w(p,v,{chat:n}),command:e,document:t,...t.revision?{expectedRevision:t.revision}:{}});if(r=l.actionCellId,o?.()===!1)return{ok:!0,message:"Frame extraction queued in the previous workspace."};ae(n),ne(r,null),oe(r,!0),Z(l.outputCellId??r,n),M(n,()=>h(`Frame extraction queued for ${a}`));const u=await Pt({bookId:i,notebookId:t.id,cellId:r,address:Se(s.slot),runId:l.runId,jobOperationId:l.jobId,intervalMs:wn,timeoutMs:hn,maxPollFailures:fr});if(o?.()===!1)return{ok:!0,message:"Check the previous workspace for the accepted frame extraction."};if(u.kind==="failed")throw new Error(u.message??`Frame extraction for ${a} failed`);if(u.kind==="timeout")throw new Error("Frame extraction did not finish within five minutes");if(u.kind==="superseded")throw new Error(`Frame extraction for ${a} was superseded by a newer run`);return Z(l.outputCellId??r,n),{ok:!0,message:e.frameMode==="time"?`Extracted the frame at ${e.timestampSeconds??0}s of ${a}`:`Extracted the ${e.frameMode} frame of ${a}`}}catch(s){const a=s instanceof Error?s.message:String(s);return o?.()!==!1&&(r&&ne(r,a),M(n,()=>h(a,"error"))),{ok:!1,message:a}}finally{r&&o?.()!==!1&&oe(r,!1),T(!1)}},lu=async(e,t,o,n)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting audio."};let r=null;T(!0);try{const s=St(t,e.sourceReference),a=W(s.slot),l=await Ok({actor:"videobook-user",bookId:i,callTool:(d,p)=>w(d,p,{chat:n}),command:e,document:t,...t.revision?{expectedRevision:t.revision}:{}});if(r=l.actionCellId,o?.()===!1)return{ok:!0,message:"Audio extraction queued in the previous workspace."};ae(n),ne(r,null),oe(r,!0),Z(l.outputCellId??r,n),M(n,()=>h(`Audio extraction queued for ${a}`));const u=await Pt({bookId:i,notebookId:t.id,cellId:r,address:Se(s.slot),runId:l.runId,jobOperationId:l.jobId,intervalMs:wn,timeoutMs:hn,maxPollFailures:fr});if(o?.()===!1)return{ok:!0,message:"Check the previous workspace for the accepted audio extraction."};if(u.kind==="failed")throw new Error(u.message??`Audio extraction for ${a} failed`);if(u.kind==="timeout")throw new Error("Audio extraction did not finish within five minutes");if(u.kind==="superseded")throw new Error(`Audio extraction for ${a} was superseded by a newer run`);return Z(l.outputCellId??r,n),{ok:!0,message:`Extracted audio from ${a}`}}catch(s){const a=s instanceof Error?s.message:String(s);return o?.()!==!1&&(r&&ne(r,a),M(n,()=>h(a,"error"))),{ok:!1,message:a}}finally{r&&o?.()!==!1&&oe(r,!1),T(!1)}},li=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting audio."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");return St(n,e.sourceReference),L(o,!1,()=>le(null)),L(o,!1,()=>O(null)),await lu(e,n,t,o)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},ci=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting a frame."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");return St(n,e.sourceReference),L(o,!1,()=>le(null)),L(o,!1,()=>O(null)),await ii(e,n,t,o)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},di=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before extracting a frame."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");const r=St(n,e.sourceReference),s=e.frameMode==="time"?`Extract the frame at ${e.timestampSeconds??0}s from ${W(r.slot)}`:`Extract the ${e.frameMode} frame from ${W(r.slot)}`;return L(o,!1,()=>le(null)),L(o,!0,()=>O({kind:"frame",command:e,expectations:[{address:W(r.slot),cellId:r.id}],notebookId:n.id,reason:"This request extracts a frame into a new image cell",summary:s})),pt("Frame extraction ready to apply")}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},cn=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before splitting a video."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");const r=St(n,e.sourceReference),s=dr(n,r),a=s?re.get(s):void 0,l=a?.duration??ie(r.inputs?.durationSeconds);if(!a?.mediaUrl)throw new Error(`${W(r.slot)} does not have playable video yet`);const u=gn.maximumRowCount*gn.columnCount,d=e.outputMode??"all",p=e.cutPointsSeconds.filter(R=>l===null||Math.abs(R-l)>.001),v=d==="all"?ek({cutPointsSeconds:p,sourceDurationSeconds:l??Number.NaN}):yl({cutPointsSeconds:p,sourceDurationSeconds:l??Number.NaN}).slice(0,-1).map(R=>R.endSeconds),S={...e,cutPointsSeconds:v,outputMode:d,selectedChunkIndexes:e.selectedChunkIndexes??(d==="all"?[0]:e.selectedChunkIndexes??[0])},A=yl({cutPointsSeconds:v,sourceDurationSeconds:l??Number.NaN}).length,y=tk(d,A);if(u-n.cells.length<y)throw new Error(`The notebook needs ${y} empty cells to split a video`);return L(o,!1,()=>le(null)),L(o,!0,()=>O({kind:"split",command:S,expectations:[{address:W(r.slot),cellId:r.id}],notebookId:n.id,reason:"This request creates and runs a Split Video workflow",sourceDurationSeconds:l??Number.NaN,summary:Ji({cutPointsSeconds:v,outputMode:d,selectedChunkIndexes:S.selectedChunkIndexes,sourceAddress:W(r.slot),sourceDurationSeconds:l??Number.NaN})})),pt("Video split ready to apply")}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},cu=async(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a notebook before generating media."};try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:c.id},{chat:o}));if(t?.isCurrent?.()===!1)return{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."};if(!n)throw new Error("The server returned an invalid notebook");let r=Ql({actions:Qe,cellId:xt(),command:e,document:n,fallbackSlot:Mo(e.cellType,n.cells,Ge),lastWorkSlot:Ge,...t?.preferredModel?{preferredModel:t.preferredModel}:{},...t?.routedParams?{routedParams:t.routedParams}:{}});const s=r.sourceCellIds.flatMap(l=>{const u=n.cells.find(d=>d.id===l);return u?[u]:[]});if(r=tr(r,kk(e.prompt,se,s)),r.cell.type==="generate_audio"&&r.action.controls.some(l=>l.name==="voice_id")&&typeof sl(r).voice_id!="string"){const l=bk(Hn.voices,wk());l&&(r=xs(r,"voice_id",l))}hk(r,n);const a=r.sourceCellIds.length>0?` from ${r.sourceCellIds.flatMap(l=>{const u=n.cells.find(d=>d.id===l);return u?[W(u.slot)]:[]}).join(", ")}`:"";return L(o,!1,()=>le(null)),L(o,!0,()=>O({kind:"generation",draft:r,notebookId:n.id,preview:null,previewError:null,previewLoading:!0,previewStale:!1,expectations:[...r.sourceCellIds.flatMap(l=>{const u=n.cells.find(d=>d.id===l);return u?[{address:W(u.slot),cellId:u.id}]:[]}),{address:W(r.cell.slot),cellId:null}],reason:t?.reason??"Generation can incur provider spend and sends the prompt and required references",summary:`Generate ${e.mediaKind} as ${W(r.cell.slot)}${a}`})),jt(r,n,o),Bl(`Generation ready to apply as ${W(r.cell.slot)}`)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},rs=e=>e==="completed"||e==="failed"||e==="cancelled"||e==="interrupted"||e==="awaiting-approval",ui=async(e,t,o,n)=>{Ot("videobook.active-chain",JSON.stringify({bookId:e,chainId:t.chainId}));const r=Date.now()+5*6e4;let s=t;for(;Date.now()<r;){const a=Ls(await w("chain",{action:"status",book_id:e,chain_id:t.chainId},{background:!0,chat:n}));if(o?.()===!1)throw new Error("Workspace changed. Check the previous project for the accepted action.");if(!a)break;s=a;const l=a.steps.find(u=>u.status==="running");if(l&&M(n,()=>h(`${l.tool.replaceAll("_"," ")}…`)),rs(a.status))return a.status!=="awaiting-approval"&&Ot("videobook.active-chain",""),a;await new Promise(u=>window.setTimeout(u,250))}throw new Error(s.error??"Chain timed out")},fi=(e,t)=>{const n=e.steps.find(s=>s.id===e.awaitingStepId)?.review;if(!n)return{ok:!1,message:"The chain is waiting for approval but sent no review."};const r=e.steps.filter(s=>s.status==="pending").length;return L(t,!0,()=>O({kind:"chain-step",chainId:e.chainId,review:n,remaining:r})),M(t,()=>h(n.reason)),{ok:!0,message:n.reason,nextInput:"/apply",selectInput:!1}},du=async(e,t)=>{if(!i)return{ok:!1,message:"Load or create a book first."};L(t,!1,()=>O(null)),T(!0);try{const o=Ls(await w("chain",{action:"approve",book_id:i,chain_id:e.chainId,step_id:e.review.stepId,actor:"chat"},{chat:t}));if(!o)throw new Error("The server did not return the chain run");const n=rs(o.status)?o:await ui(i,o,void 0,t);if(n.status==="awaiting-approval")return fi(n,t);if(await F(i,c?.id,void 0,t),n.status!=="completed")throw new Error(n.error??`Chain ${n.status}`);const r="Chain complete";return M(t,()=>h(r)),{ok:!0,message:r}}catch(o){const n=o instanceof Error?o.message:String(o);return M(t,()=>h(n,"error")),{ok:!1,message:n}}finally{T(!1)}},mi=async(e,t,o)=>{if(!i)return{ok:!1,message:"Load or create a book first."};L(o,!1,()=>le(null)),T(!0);let n=!1;try{const r=await w("chat",{book_id:i,action_plan:e},{chat:o});if(n=!0,t?.()===!1)return{ok:!1,message:"Workspace changed. Check the previous project for the accepted action."};L(o,!1,()=>O(null));const s=Ls(r),a=s&&!rs(s.status)?await ui(i,s,t,o):s;if(a?.status==="awaiting-approval")return fi(a,o);const l=a;if(a&&a.status!=="completed")throw new Error(a.error??`Chain ${a.status}`);if(t?.()===!1)return{ok:!0,message:"Action accepted in the previous workspace."};if(hl(r)){const A=await Bn(r,Kl(e.prompt),t,o);return t?.()===!1?A:(M(o,()=>h(A.message,A.ok?"info":"error")),A.ok?A:{...A,nextInput:"",selectInput:!1})}const u=c?Il(e.tool,r,c.cells,Ge):[];if(c&&u.length>0){const A=[];let y=null;for(const q of u){if(t?.()===!1)return{ok:!0,message:"Action accepted in the previous workspace."};const V=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:q},{chat:o})),X=_(V?.id);if(!X)throw new Error("The server did not return the new notebook cell");y??=X,A.push(W(q.slot))}if(t?.()===!1)return{ok:!0,message:"Action accepted in the previous workspace."};Z(y,o),await F(i,c.id,t,o),ae(o);const R=`Created ${A.join(" and ")}`;return t?.()!==!1&&M(o,()=>h(R)),{ok:!0,message:R}}const d=D(r),p=_(d?.cell_id),v=await F(i,c?.id,t,o);if(t?.()===!1)return{ok:!0,message:"Action accepted in the previous workspace."};p&&Z(p,o),ir(c,v)&&ae(o);const S=l?e.message||"Chain complete":kn(r,e.message||"Action applied");return M(o,()=>h(S)),{ok:!0,message:S}}catch(r){const s=r instanceof Error?r.message:String(r);if(t?.()===!1)return{ok:!1,message:s};const a=n?`Action completed, but its notebook result could not be shown: ${s}`:s;return n&&await F(i,c?.id,t,o).catch(()=>{}),M(o,()=>h(a,"error")),{ok:!1,message:a,nextInput:n?"":"/apply",selectInput:!n}}finally{T(!1)}},uu=async(e,t,o)=>{if(!i||!c||e.tool!=="post"&&e.routedTool!=="post")return null;const r=(_(e.params.asset_id)?.trim()??"").replace(/^@/,""),s=se.find(y=>y.artifactId===r||y.cellAddress.toLowerCase()===r.toLowerCase()),a=s?.artifactId??r,l=re.get(a)??s;if(!a||l?.type!=="video"&&l?.type!=="final")return null;const u=c.posts?.find(y=>y.id===e.params.post_cell_id),d=vk(c,u?.definition.source?.artifactId??a),p=[...H.map(y=>({reference:y.artifactId,type:y.type})),...se.map(y=>({reference:y.cellAddress,type:y.type}))],v=await Promise.all(d.steps.map(async y=>{const R=await w("list_cell_generations",{book_id:i,notebook_id:c.id,cell_id:y.outputCellId??y.producerCellId,limit:20},{background:!0,chat:o}).catch(()=>null),q=D(R)?.attempts,V=Array.isArray(q)?q:[],X=yk(Ik({attempts:V,outputArtifactId:y.outputArtifactId,outputAssetPrompt:y.outputArtifactId?re.get(y.outputArtifactId)?.prompt??null:null,producerResolvedPrompt:y.producerResolvedPrompt,producerPrompt:y.producerPrompt}),p),P=y.sourceArtifactIds.flatMap(B=>{const te=re.get(B);if(te?.type!=="image")return[];const de=se.find(pe=>pe.artifactId===B);return[{assetId:B,label:de?`@${de.cellAddress}`:te.id,mediaUrl:te.mediaUrl,thumbnailUrl:te.thumbnailUrl}]}),N=Ck({attempts:V,outputArtifactId:y.outputArtifactId,producerTool:y.producerTool,producerModel:y.producerModel,producerProvider:y.producerProvider,actions:Qe});return{id:y.id,prompt:X,model:N,images:P}})),S=await Promise.all(d.upstreamArtifactIds.filter(y=>{const R=re.get(y);return R?.origin==="download"&&(R.type==="video"||R.type==="final")}).map(async y=>{const R=await w("read_asset_metadata",{asset_id:y,name:"original",book_id:i},{background:!0,chat:o}).catch(()=>null),q=D(R);return q?Sk(y,q):null})),A=xk(S.filter(y=>y!==null));return Ek({steps:v,credits:A},t)},fu=async e=>{const t=e.definition.source?.snapshotArtifactId;if(!t)return;const o={kind:"chat-action-plan",planId:xt(),bookId:i,prompt:`Post ${e.address} to X`,routedTool:"post",tool:"post",params:{book_id:i,asset_id:t,post_cell_id:e.id,platform:"x",text:e.definition.caption},message:"Review your X publication",summary:"Publish the saved clip to X",effect:"mutation",confirmation:{required:!0,reason:"Publishes this clip to X"}};await Kn(o,o.prompt),me(!0)},ss=(e,t)=>{if(g.state!=="ready"||!i||!c)return{ok:!1,message:"Open a connected notebook before making a cold open."};const o=e?.replace(/^@/,""),n=o?se.find(l=>l.artifactId===o||l.cellAddress.toLowerCase()===o.toLowerCase()):null,r=n?.artifactId??o??$?.outputArtifactId,s=r?re.get(r):null;if(!s||!["video","final"].includes(s.type)||!s.mediaUrl)return{ok:!1,message:"Select a playable video or use /edit-cold-open @a1."};const a=s.mediaUrl;return L(t,!1,()=>le(null)),L(t,!1,()=>Te(null)),L(t,!0,()=>O({kind:"cold-open",review:{bookId:i,notebookId:c.id,assetId:s.artifactId,label:n?`@${n.cellAddress}`:s.label??s.id,mediaUrl:a,requestId:xt(),suggestion:null}})),me(!0),pt("Cold-open review opened")},dn=c?.posts??[],as=(e,t)=>w(e,t,{background:!0}),ut=e=>O(t=>t?.kind==="post-delivery"?{...t,review:{...t.review,...e}}:t),is=async()=>{try{ut({connection:await Bp(as)})}catch(e){ut({connection:{connected:!1,pending:!1,hasCredentials:!0,error:e instanceof Error?e.message:String(e)}})}},mu=async()=>{try{const e=await Ak(as);O(t=>t?.kind==="post-delivery"?{...t,review:_k(t.review,e)}:t)}catch(e){ut({icloud:{available:!1,root:"",shared:null,role:null,reason:e instanceof Error?e.message:String(e)}})}},pu=async()=>{const e=window.open("about:blank","_blank");ut({connecting:!0});try{const t=await Kp(w);e?e.location.href=t:window.open(t,"_blank","noopener,noreferrer");const o=Q.current.bookId,n=await Jp(as,rt,()=>Q.current.bookId===o);ut({connection:n,connecting:!1})}catch(t){e?.close(),ut({connecting:!1,connection:{connected:!1,pending:!1,hasCredentials:!0,error:t instanceof Error?t.message:String(t)}})}},ls=(e,t,o)=>{if(g.state!=="ready"||!i||!c)return{ok:!1,message:"Open a connected notebook before delivering a Post."};const n=ul(dn,c.cells,e,$?.id??null),r=t==="dropbox"?"/upload-post-to-dropbox @b1":"/save-post-to-icloud @b1";return n?us(n,t,o):{ok:!1,message:e?.trim()?`${e.trim()} is not a Post or a clip. Select one or use ${r}.`:`Select a Post cell or use ${r}.`}},cs=async(e,t,o)=>{const n=e?.trim(),r=n&&g.state==="ready"&&i&&c&&!ul(dn,c.cells,n,null)?ck(c.cells,n):null;if(!r||!i||!c)return ls(e,t,o);const s=dk(dn,r.id);if(s)return us(s,t,o);try{const a=await w("create_post",{book_id:i,notebook_id:c.id,source_cell_id:r.id});return await F(i,c.id),us(a,t,o)}catch(a){return{ok:!1,message:a instanceof Error?a.message:String(a)}}},ds=async(e,t,o,n,r)=>{const s=xt(),a=l=>l?.kind==="post-delivery"&&l.review.postId===t&&l.review.copy.drafting?.requestId===s;O(l=>l?.kind==="post-delivery"&&l.review.postId===t?{...l,review:{...l.review,copy:{...l.review.copy,drafting:{requestId:s,language:n},error:null}}}:l);try{const l=Pg(await w("draft_post_copy",Mg(e,t,o,n,r)));O(u=>a(u)&&u?.kind==="post-delivery"?{...u,review:{...u.review,copy:Tg(u.review.copy,n,l,r)}}:u)}catch(l){const u=l instanceof Error?l.message:String(l);O(d=>a(d)&&d?.kind==="post-delivery"?{...d,review:{...d.review,copy:{...d.review.copy,drafting:null,error:u}}}:d)}},gu=(e,t,o)=>{const n={...t.copy,language:o};ut({copy:n}),dl(n,o,js(e))&&ds(t.bookId,e.id,n,o,null)},ku=(e,t)=>{js(e)||t.copy.drafting||ds(t.bookId,e.id,t.copy,t.copy.language,t.copy.prompt.trim()||null)},us=(e,t,o)=>{if(!i||!c)return{ok:!1,message:"Open a connected notebook before delivering a Post."};const n=uo?.name??"book",r=Og(e);return L(o,!1,()=>le(null)),L(o,!1,()=>Te(null)),L(o,!0,()=>O({kind:"post-delivery",review:{bookId:i,notebookId:c.id,postId:e.id,entry:t,destination:t,pinnedDestination:!1,copy:r,icloudFolder:Gg(e,n),dropboxFolder:Vg(e,n),connection:null,connecting:!1,icloud:null,receipt:null,sync:null}})),me(!0),mu(),t==="dropbox"&&is(),dl(r,r.language,js(e))&&ds(i,e.id,r,r.language,null),pt(t==="dropbox"?"Dropbox upload review opened":"Save to iPhone review opened")},bu=e=>{ut({destination:e,pinnedDestination:!0}),e==="dropbox"&&is()},Kn=async(e,t,o,n)=>{const r=d=>{const p=_(d);return p?sr(Ns(p.startsWith("@")?p:`@${p}`,se))[0]??null:null};if(e.tool==="prepare_cold_open"||e.tool==="edit_cold_open")return ss(_(e.params.asset_id)??void 0,n);if(e.tool==="upload_post_to_dropbox"||e.tool==="save_post_to_icloud")return cs(_(e.params.post_cell_id)??void 0,e.tool==="upload_post_to_dropbox"?"dropbox":"icloud",n);if(e.tool==="show_media_fullscreen"){const d=Eg(e.params,c?.cells??[],H);return d.ok?o?.()===!1||n?.isCurrent()===!1?{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."}:(L(n,!1,()=>O(null)),L(n,!1,()=>le(null)),Vn(d.cell,d.asset),{ok:!0,message:`Opened ${d.address} fullscreen`}):d}if(e.tool==="apply_watermark"||e.routedTool==="apply_watermark"){const d=_(e.params.asset_id)?.replace(/^@/,""),v=(d?se.find(Oe=>Oe.artifactId===d||Oe.cellAddress.toLowerCase()===d.toLowerCase()):void 0)?.artifactId??d,S=kl(v,$,H,new Map(se.map(Oe=>[Oe.artifactId,Oe.cellAddress])));if(!S.ok)return{ok:!1,message:S.message};const A=ie(e.params.qr_start_seconds),y=ie(e.params.qr_end_seconds),R=ie(e.params.handle_start_seconds),q=ie(e.params.handle_end_seconds),V=ie(e.params.qr_opacity),X=ie(e.params.handle_opacity),P=ie(e.params.handle_vertical_percent),N=ie(e.params.handle_padding),B=ie(e.params.handle_padding_y),te=ie(e.params.handle_rounding),de=ie(e.params.fade_seconds),pe=e.params.position,Be=e.params.handle_position,be=e.params.include_platform_icon;return Ha(S.artifactId,S.label,{...Ag(e.params.platform)?{platform:e.params.platform}:{},..._(e.params.handle)?{handle:_(e.params.handle)??void 0}:{},..._(e.params.url)?{url:_(e.params.url)??void 0}:{},...typeof e.params.include_qr=="boolean"?{includeQr:e.params.include_qr}:{},...typeof e.params.include_handle=="boolean"?{includeHandle:e.params.include_handle}:{},...Bk(pe)?{position:pe}:{},...P!==null?{handleVerticalPercent:_l(P)}:{},...Hk(Be)?{handlePlacement:Be}:{},...typeof be=="boolean"?{includePlatformIcon:be}:{},...typeof e.params.include_handle_border=="boolean"?{includeHandleBorder:e.params.include_handle_border}:{},...N!==null?{handlePadding:cr(N)}:{},...B!==null?{handlePaddingY:cr(B)}:{},...te!==null?{handleRounding:Al(te)}:{},...V!==null?{qrOpacity:lr(V)}:{},...X!==null?{handleOpacity:lr(X)}:{},...A!==null&&A>=0?{qrStartSeconds:A}:{},...y!==null&&y>=0?{qrEndSeconds:y}:{},...R!==null&&R>=0?{handleStartSeconds:R}:{},...q!==null&&q>=0?{handleEndSeconds:q}:{},...de!==null?{fadeSeconds:El(de)}:{},...typeof e.params.save_default=="boolean"?{saveDefault:e.params.save_default}:{}},n),pt(`Watermark review ready for ${S.label}`)}if(e.tool==="transcribe"||e.routedTool==="transcribe")return sn({assetRef:_(e.params.asset_id)??void 0,languageCode:_(e.params.language_code)??"",diarize:typeof e.params.diarize=="boolean"?e.params.diarize:!0,tagAudioEvents:typeof e.params.tag_audio_events=="boolean"?e.params.tag_audio_events:!0,chat:n});if(e.tool==="extract_audio"){const d=r(e.params.asset_id);return d?await li({sourceReference:d},o,n):{ok:!1,message:"The chat model did not select a video source."}}if(e.tool==="extract_frame"&&(e.params.frame==="first"||e.params.frame==="last")){const d=r(e.params.asset_id);if(!d)return{ok:!1,message:"The chat model did not select a video source."};const p={frameMode:e.params.frame,sourceReference:d};return e.confirmation.required===!1?await ci(p,o,n):await di(p,o,n)}if(e.tool==="extract_frame"){const d=r(e.params.asset_id),p=ie(e.params.timestamp);if(!d||p===null||p<0)return{ok:!1,message:"The chat model did not select a valid video source and timestamp."};const v={frameMode:"time",sourceReference:d,timestampSeconds:p};return e.confirmation.required===!1?await ci(v,o,n):await di(v,o,n)}if(e.tool==="split_video"){const d=r(e.params.asset_id),p=ie(e.params.chunk_a_end);return!d||!p||p<=0?{ok:!1,message:"The chat model did not select a valid split source and time."}:await cn({sourceReference:d,cutPointsSeconds:[p]},o,n)}if(e.tool==="split_video_by_durations"&&e.params.destination===void 0){const d=r(e.params.asset_id),v=(Array.isArray(e.params.target_secs)?e.params.target_secs:[7]).map(ie);if(v.some(S=>S===null||S<=0))return{ok:!1,message:"The chat model did not select valid split durations."};if(d)return await cn({sourceReference:d,cutPointsSeconds:bl(v)},o,n)}if(e.effect==="generation"){const d=_g(e.tool,e.routedTool,Qe),p=_(e.params.prompt)??t,v=Ns(p,se),S=Rg(e.params).map(q=>Ns(`@${q}`,se)).join(" "),A=sr(S),y=sr(v),R={cellType:d,mediaKind:Gs(d),prompt:p,sourceReferences:A.length>0?A:y.length>0?y:sr(t)};return await cu(R,{isCurrent:o,..._(e.params.model)?{preferredModel:_(e.params.model)}:{},reason:e.confirmation.reason,routedParams:e.params},n)}if(e.confirmation.required===!1)return await mi(e,o,n);const a=e.tool==="post"||e.routedTool==="post"?await Ka():null,l=await uu(e,Zn(a??$o.status),n),u=l?{...e,params:pn(e.params,to(l))}:e;return o?.()===!1?{ok:!1,message:"Workspace changed. Repeat the command in the current workspace."}:(L(n,!1,()=>le(null)),L(n,!0,()=>O({kind:"routed",plan:u,xPostReview:l})),pt("Action preview ready"))},wu=(e,t)=>{const o=Ss({...t,cells:[e.cell],edges:[]},H,Ve)[0];if(!o)return;const n=new Date().toISOString();ht(r=>r.some(s=>s.id===o.id)?r.map(s=>s.id===o.id?{...o,data:{...o.data,status:"queued",statusStartedAt:n}}:s):[...r,{...o,data:{...o.data,status:"queued",statusStartedAt:n}}])},hu=async(e,t=null,o)=>{const n=t?{...e,draft:tr(e.draft,t)}:e,r=t?`/apply ${t}`:"/apply ";if(!n.draft.cell.prompt?.trim())return{ok:!1,message:"Enter a generation prompt before applying.",nextInput:r,selectInput:!1};if(!i||!c||c.id!==n.notebookId)return{ok:!1,message:"The generation draft belongs to another notebook."};let s;try{const A=ge(await w("get_notebook",{book_id:i,notebook_id:n.notebookId},{chat:o}));if(!A)throw new Error("The server returned an invalid notebook");s=A}catch(A){return{ok:!1,message:A instanceof Error?A.message:String(A),nextInput:r,selectInput:!1}}if(Pl(s,n.expectations))return L(o,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."};if(!_t)return{ok:!1,message:"Offline: cloud generation is unavailable.",nextInput:r,selectInput:!1};M(o,()=>O(A=>A?.kind==="generation"&&A.draft.cell.id===n.draft.cell.id?{...A,draft:n.draft,previewError:null,previewLoading:!0,previewStale:!1}:A));let a;try{$t.cancel(),vo.current+=1,a=await Xr(n.draft,s,o)}catch(A){const y=A instanceof Error?A.message:String(A);return M(o,()=>O(R=>R?.kind==="generation"&&R.draft.cell.id===n.draft.cell.id?{...R,draft:n.draft,previewError:y,previewLoading:!1,previewStale:!1}:R)),{ok:!1,message:y,nextInput:r,selectInput:!1}}M(o,()=>O(A=>A?.kind==="generation"&&A.draft.cell.id===n.draft.cell.id?{...A,draft:n.draft,preview:a,previewError:null,previewLoading:!1,previewStale:!1}:A));const l=Uk(a);if(l)return{ok:!1,message:l,nextInput:r,selectInput:!1};const u="videobook.cloud-generation-consent";if(window.localStorage.getItem(u)!=="accepted"){if(!window.confirm(`Cloud generation disclosure
|
|
32
32
|
|
|
33
33
|
Provider/model: ${n.draft.action.provider} · ${n.draft.action.model}
|
|
34
34
|
Payload class: prompt text and connected media references.
|
|
35
35
|
Your local source files are sent only when required by the selected model.
|
|
36
36
|
|
|
37
|
-
Continue and remember this choice on this device?`))return{ok:!1,message:"Cloud generation cancelled before sending data",nextInput:r,selectInput:!1};window.localStorage.setItem(u,"accepted")}const d=n.draft.cell.id,p=W(n.draft.cell.slot);let v=!1,S=!1;T(!0),ne(d,null),oe(d,!0),Ae(n.draft.cell.slot),Z(d,o,a),bu(n.draft,s);try{await vl({bookId:i,callTool:(H,te)=>w(H,te,{chat:o}),document:s,draft:n.draft,...s.revision?{expectedRevision:s.revision}:{}}),v=!0;const A=await ko(d,"chat",o),y=await w("run_notebook_cell",{book_id:i,notebook_id:s.id,cell_id:d,plan:A,actor:"videobook-user"},{chat:o});S=!0;const R=D(y);ae(o);const q=_(R?.run_id),V=_(R?.job_id),X=_(R?.output_cell_id);if(L(o,!1,()=>O(null)),$r.current||go(),oe(d,!1),!q||!V)return await F(i,s.id,void 0,o).catch(()=>{}),{ok:!0,message:`${p} was accepted; follow its status in Jobs`};M(o,()=>h(`${p} queued`));const P=X??d;let N=Se(n.draft.cell.slot);if(X){const H=await $e(i,s.id,o).catch(()=>null);M(o,()=>{en([X]),po([X],{scroll:"center"})}),ne(X,null),oe(X,!0);const te=H?.cells.find(de=>de.id===X);te&&(N=Se(te.slot))}else po([d],{scroll:"center"});return tn({bookId:i,notebookId:s.id,cellId:P,address:N,runId:q,jobOperationId:V},o),await F(i,s.id,void 0,o).catch(()=>{}),{ok:!0,message:`${p} queued`}}catch(A){const y=A instanceof Error?A.message:String(A),R=y.startsWith("Stale notebook revision:");return v&&!S&&await w("delete_notebook_cell",{book_id:i,notebook_id:s.id,cell_id:d},{chat:o}).catch(()=>{}),S||(ht(q=>q.filter(V=>V.id!==d)),oe(d,!1)),ne(d,y),await F(i,s.id,void 0,o).catch(()=>{}),R?(L(o,!1,()=>O(null)),M(o,()=>h("Notebook changed since this preview; prepare the action again.","error")),{ok:!1,message:"Notebook changed since this preview; prepare the action again."}):(M(o,()=>h(y,"error")),{ok:!1,message:y,nextInput:r,selectInput:!1})}finally{T(!1)}},pi=async(e,t,o)=>{const n=t??e.languageCode,r=rl({assetId:e.assetId,languageCode:n}),s=t?`/apply ${t}`:"/apply ";if(r.blocking||!e.assetId||!i)return{ok:!1,message:r.blocking??"Choose a video or audio clip.",nextInput:s,selectInput:!1};const a=e.assetId,l=na[a]??Qi;if(Dk(l))return{ok:!1,message:"Transcription is already running for this clip.",nextInput:s,selectInput:!1};t!==null&&t!==e.languageCode&&M(o,()=>O(y=>y?.kind==="transcribe"?{...y,languageCode:n}:y));const u=c?.id,d=zl(re.get(a),"transcript"),p=Date.now();rn(a,{...bn("transcript",!0),error:null});try{await w("transcribe",cl({bookId:i,assetId:a,languageCode:n,diarize:e.diarize,tagAudioEvents:e.tagAudioEvents}),{chat:o})}catch(y){const R=y instanceof Error?y.message:String(y);return rn(a,{...bn("transcript",!1),error:R}),{ok:!1,message:R,nextInput:s,selectInput:!1}}L(o,!1,()=>O(null));const v=se.find(y=>y.artifactId===a)?.cellAddress,A=`Transcription queued for ${v?`@${v}`:re.get(a)?.label??a}`;return M(o,()=>h(A)),u?gd({bookId:i,notebookId:u,artifactId:a,insight:"transcript",since:p,hadInsight:d}).then(y=>{rn(a,{...bn("transcript",!1),error:y.kind==="failed"?y.message:null})}).catch(y=>{rn(a,{...bn("transcript",!1),error:y instanceof Error?y.message:String(y)})}):rn(a,{...bn("transcript",!1),error:null}),{ok:!0,message:A,nextInput:""}},hu=async(e=null,t)=>{if(!E||!i)return{ok:!1,message:"There is no pending chat action."};if(E.kind==="cold-open"){const o=E.review,n=()=>Q.current.bookId===o.bookId&&Q.current.notebookId===o.notebookId&&(t?.isCurrent()??!0),r=(a,l,u)=>w(a,l,{...u,chat:t});if(!o.suggestion){const a=await Ak(r,o,n);return L(t,!0,()=>O({kind:"cold-open",review:a})),pt("Adjust the highlight, then create the copy")}const s=await _k(r,o,n);return await F(o.bookId,o.notebookId,n,t),n()?(L(t,!1,()=>O(null)),Z(s.cellId),ae(t),{ok:!0,message:`Cold-open copy created as ${s.address}`}):{ok:!0,message:`Cold-open copy created as ${s.address}`}}if(E.kind==="post-delivery"){const o=E.review,n=dn.find(d=>d.id===o.postId)??null,r=al(n,o);if(!n||r.blocking)return{ok:!1,message:r.blocking??"This Post is no longer on the canvas."};const s=()=>Q.current.bookId===o.bookId&&Q.current.notebookId===o.notebookId&&(t?.isCurrent()??!0),a=Rk(n,o);a&&await w("update_post",a,{chat:t});const l=await w(Pk(o.destination),Mk(n,o),{chat:t});await F(o.bookId,o.notebookId,s,t);const u=Tk(l,o.destination);return s()&&L(t,!0,()=>O({kind:"post-delivery",review:{...o,icloudFolder:l.runtime.icloud?.folder??o.icloudFolder,dropboxFolder:l.runtime.dropbox?.folder??o.dropboxFolder,receipt:u,sync:null}})),{ok:!0,message:u}}if(E.kind==="transcribe"){if(e){const o=jk(e);return o.ok?await pi(E,o.languageCode,t):{ok:!1,message:o.message,nextInput:`/apply ${e}`,selectInput:!1}}return await pi(E,null,t)}if(E.kind==="generation")return await wu(E,e,t);if(E.kind==="routed"&&(E.plan.tool==="post"||E.plan.routedTool==="post")){const o=Oi(Fi(E.plan.params),void 0,Sn),n=E.xPostReview?.options.enabled&&eo(E.xPostReview).length===0?Di:null;if(o||n)return{ok:!1,message:o??n??"The post is not ready.",nextInput:"/apply",selectInput:!1}}if(E.kind==="frame"||E.kind==="split"||E.kind==="notebook"){const o=ge(await w("get_notebook",{book_id:i,notebook_id:E.notebookId},{chat:t}));if(!o)return{ok:!1,message:"The server returned an invalid notebook"};const n=E.kind==="notebook"?E.plan.expectations:E.expectations;if(Pl(o,n))return L(t,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."};if(E.kind==="frame"){const s=await ii(E.command,o,void 0,t);if(s.ok)L(t,!1,()=>O(null));else if(s.message.startsWith("Stale notebook revision:"))return L(t,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."};return s}if(E.kind==="split"){const s=await au(E.command,o,t);if(s.ok)L(t,!1,()=>O(null));else if(s.message.startsWith("Stale notebook revision:"))return L(t,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."};return s}const r=E.plan.action;if(r.kind==="run"){const s=Po(o,r.source),a=await on(s.id,o,t);return a?.ok?(L(t,!1,()=>O(null)),{ok:!0,message:`Run requested for ${W(s.slot)}`}):a?.message.startsWith("Stale notebook revision:")?(L(t,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."}):a??{ok:!1,message:`Could not run ${W(s.slot)}`}}T(!0);try{const s=o.revision?{expected_revision:o.revision}:{};if(r.kind==="create"){const a=r.destination,l=D(await w("create_notebook_cell",{book_id:i,notebook_id:o.id,...s,cell:{type:r.cellType,slot:a,...r.cellType==="prompt"||r.cellType==="analyze"||oo(r.cellType)?{prompt:""}:{}}},{chat:t})),u=_(l?.id);u&&Z(u,t)}else if(r.kind==="move"){const a=Po(o,r.source),l=Po(o,r.destination);await w("move_notebook_cells",{book_id:i,notebook_id:o.id,...s,slots:[{id:a.id,row:r.destination.row,column:r.destination.column},...l?[{id:l.id,row:r.source.row,column:r.source.column}]:[]]},{chat:t})}else if(r.kind==="delete"){const a=Po(o,r.source);await w("delete_notebook_cell",{book_id:i,notebook_id:o.id,cell_id:a.id,...s},{chat:t})}else if(r.kind==="connect"){const a=Po(o,r.source),l=Po(o,r.target),u=r.targetInput??pl(o,{source:a.id,target:l.id,targetHandle:null});await w("set_notebook_cell_input",{book_id:i,notebook_id:o.id,source_cell_id:a.id,target_cell_id:l.id,target_input:u,...s},{chat:t})}else throw new Error("Unsupported notebook action");return L(t,!1,()=>O(null)),await F(i,o.id,void 0,t),r.kind==="create"&&ae(t),M(t,()=>h(E.plan.summary)),{ok:!0,message:E.plan.summary}}catch(s){const a=s instanceof Error?s.message:String(s);return a.startsWith("Stale notebook revision:")?(L(t,!1,()=>O(null)),M(t,()=>h("Notebook changed since this preview; prepare the action again.","error")),{ok:!1,message:"Notebook changed since this preview; prepare the action again."}):(M(t,()=>h(a,"error")),{ok:!1,message:a,nextInput:"/apply",selectInput:!0})}finally{T(!1)}}return E.kind==="chain-step"?await cu(E,t):await mi(E.plan,void 0,t)},gi=async(e,t,o,n,r)=>{if(e==="download_video"&&c)return await Hn(t,_(o.url)??"",void 0,r);const s=c?Il(e,t,c.cells,Ge):[];if(c&&s.length>0){const a=[];let l=null;for(const d of s){const p=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:d},{chat:r})),v=_(p?.id);if(!v)throw new Error("The server did not return the new notebook cell");l??=v,a.push(W(d.slot))}Q.current.bookId===i&&(Z(l,r),await F(i,c.id,void 0,r));const u=`Created ${a.join(" and ")}`;return ae(r),M(r,()=>h(u)),{ok:!0,message:u}}if(Q.current.bookId===i){const a=await F(i,c?.id,void 0,r);ir(c,a)&&ae(r)}if(e==="rename_asset"){const a=D(t),l=_(a?.label);return{ok:!0,message:l?`Renamed asset to ${l}`:"Asset renamed"}}return{ok:!0,message:kn(t,`${n} complete`)}},ki=async(e,t,o,n)=>{const r=i,s=D(await w("asset_manifest",{book_id:r,asset_id:e.artifactId},{chat:n}));if(Q.current.bookId!==r)return;const a=(Array.isArray(s?.files)?s.files:[]).flatMap(d=>{const p=_(D(d)?.name);return p?[{name:p,url:`/files/${encodeURIComponent(r)}/${encodeURIComponent(e.artifactId)}/${p.split("/").map(encodeURIComponent).join("/")}`}]:[]}),l=t==="original"?a.find(d=>d.name.startsWith("original.")):t?a.find(d=>d.name.startsWith(`${t}.`)):o?a[o-1]:void 0;if((t||o)&&!l)throw new Error(t?`No ${t} file exists yet. Use render video to create it.`:"That file position does not exist.");const u=document.activeElement instanceof HTMLElement?document.activeElement:null;M(n,()=>jo({media:{label:e.label,assetId:e.artifactId,type:e.type,url:e.mediaUrl,thumbnailUrl:e.thumbnailUrl,files:a,initialFile:l?.name,opener:u},opener:u,turnId:n?.id}))},bi=async(e,t,o)=>{if(e.handler.kind!=="ui")return null;const n=e.handler.action,r=ek[n];if(r.kind==="existing")return null;if(r.kind==="library")return os(),{ok:!0,message:"Library opened"};if(r.kind==="screen")return Ao(r.screen),{ok:!0,message:`${r.screen==="jobs"?"Jobs":"Settings"} opened`};const s=_(t.asset_id??t.asset_ref??t.artifact_id)??Ne?.media?.assetId??Y?.asset.artifactId??$?.outputArtifactId,a=B.find(l=>l.artifactId===s)??B.find(l=>se.some(u=>u.artifactId===l.artifactId&&u.cellAddress.toLowerCase()===s?.replace(/^@/u,"").toLowerCase()));if(r.kind==="search")return await Ce(void 0,void 0,r.query,void 0,o),{ok:!0,message:"Actions opened"};if(r.kind==="form"){const l=e.command==="/storage"?"storage_status":r.tool,u=J?J.frameRate.numerator/J.frameRate.denominator:30,d=tk(n,t,u);if(a&&(d.asset_id=a.artifactId),n.startsWith("timeline_audio_")&&n!=="timeline_audio_add"&&t.audio_ref){const p=ok(String(t.audio_ref),J,B,se);if(!p.ok)return p;d.audio_id=p.clipId}return n==="viewer_focus_file"&&a?await ki(a,void 0,nk(t.position),o):await Ce(`tool.${l}`,d,void 0,void 0,o),{ok:!0,message:`${e.title} options opened`}}if(r.action==="upload")return Bs.current?.click(),{ok:!0,message:"Choose files to import"};if(r.action==="notebook"){const l=_(t.name)?.trim();if(l){const d=Zi(await w("list_notebooks",{book_id:i},{chat:o})).find(p=>p.name===l||p.id===l);if(!d)return await Ce("tool.create_notebook",{name:l},void 0,void 0,o),{ok:!0,message:"Create notebook options opened"};await F(i,d.id,void 0,o)}else if(!c)return await Ce("tool.create_notebook",{name:"scratch"},void 0,void 0,o),{ok:!0,message:"Create notebook options opened"};return Ao("notebook"),{ok:!0,message:"Notebook opened"}}if(r.action==="save"){if(!c)throw new Error("Open a notebook first.");return await $e(i,c.id,o),{ok:!0,message:"Notebook changes are saved automatically. Saved state verified."}}if(r.action==="collapse"||r.action==="expand"){const l=r.action==="expand",u=rk(_(t.side));return u!=="left"&&(!l||no("expand"))&&me(l),u!=="right"&&(l?await Co():Pr(!1)),{ok:!0,message:l?"Workspace panels opened":"Workspace panels closed"}}if(r.action==="close")return Kt(),M(o,()=>jo(null)),{ok:!0,message:"Viewer closed"};if(r.action==="play"){const l=sk(_(t.slot),J);return l.ok?(M(o,()=>jo({initialFrame:l.initialFrame,turnId:o?.id,opener:document.activeElement instanceof HTMLElement?document.activeElement:null})),{ok:!0,message:"Sequence preview opened"}):{ok:!1,message:l.message}}if(!a)return await Ce(e.id,t,void 0,void 0,o),{ok:!0,message:"Choose media for this action"};if(r.action==="copy")return await navigator.clipboard.writeText(a.label),{ok:!0,message:"Media label copied"};if(r.action==="history"){const l=c?.cells.find(u=>u.outputArtifactId===a.artifactId);return l?Ci(l.id,a.artifactId):await Ce("tool.asset_history",{asset_id:a.artifactId},void 0,void 0,o),{ok:!0,message:"Media history opened"}}if(r.action==="skeleton"){if(a.type!=="image")throw new Error("Choose an image for a pose guide.");return await Ce("tool.generate_image",{model:"kie:qwen3/image-to-image",refs:{image:[a.artifactId]},prompt:"Create a pose skeleton guide from this reference image. Preserve the visible body poses, joint positions and framing. Show only clearly connected colored skeleton joints and limbs on a black background, without clothing, faces, scenery or text."},void 0,void 0,o),{ok:!0,message:"AI pose guide options opened. Review the provider and cost before generating."}}return await ki(a,r.action==="open"?void 0:r.action,void 0,o),{ok:!0,message:"Media preview opened"}},fs=async(e,t,o)=>{try{const n=e.trim().toLowerCase(),r=qs(e);if(r)return r.promptOverride&&(he||E?.kind!=="generation"&&E?.kind!=="transcribe")?{ok:!1,message:"A quick prompt can only revise a pending generation.",nextInput:e,selectInput:!1}:he?await Vd(o):E?await hu(r.promptOverride,o):ue?await Xd(o):{ok:!1,message:"There is no pending action to apply."};if(n==="/cancel")return!he&&!E&&!ue?{ok:!1,message:"There is no pending action to cancel."}:(L(o,!1,()=>Te(null)),L(o,!1,()=>O(null)),L(o,!1,()=>le(null)),{ok:!0,message:"Pending action cancelled"});if(he&&L(o,!1,()=>Te(null)),!i&&!e.startsWith("/"))return{ok:!1,message:"Load or create a book first."};if(!e.startsWith("/")){const P=await w("chat",{book_id:i,...c?{notebook_id:c.id}:{},prompt:e,model:Hs},{chat:o});return D(P)?.kind==="chat-action-plan"?await Kn(Ts(P),e,void 0,o):(L(o,!1,()=>O(null)),L(o,!1,()=>le(null)),hl(P)?await Hn(P,Kl(e),void 0,o):(await F(i,c?.id,void 0,o),{ok:!0,message:kn(P,"Command complete")}))}const[s,...a]=e.trim().split(/\s+/),l=s.toLowerCase(),u=a.join(" ");if(l==="/goal")return await wd(u,o);if(l.toLowerCase()==="/actions")return await Ce(void 0,void 0,u,void 0,o),{ok:!0,message:"Actions opened"};const d=l.toLowerCase()==="/duplicate"?[ar(a[0]??"",Uo),...a.slice(1)].filter(Boolean).join(" "):ar(u,Uo);if(l==="/transcribe"){const P=d.split(/\s+/).find(N=>N.length>0);return sn({assetRef:P,chat:o})}const p=Et.length?Et:As(await w("list_workspace_actions",{detail:"full"},{chat:o})).actions;Et.length||kr(p);const v=Dl(or(p,In),l,d),S=p.find(P=>[P.command,...P.aliases].includes(l));if(v?.workspaceActionId||S&&!u&&(S.inputSchema.required??[]).some(P=>!["book_id","notebook_id","sequence_id"].includes(P))){const P=v?mt(d,v.params):{};return await Ce(S?.id??v?.workspaceActionId,P,void 0,void 0,o),{ok:!0,message:"Action options opened"}}if(l==="/extract-audio")return!c||a.length!==1?{ok:!1,message:"Usage: /extract-audio @video"}:await li({sourceReference:pr(a[0])},void 0,o);if(l==="/split"){const P=Vg(e);return P?await cn(P,void 0,o):{ok:!1,message:"Usage: /split @video [at 5s, 12.5s] | keep 0.03-0.11 | remove 0.03-0.11"}}if((l==="/split-chunks"||l==="/even-split")&&new RegExp(`^@${Yl}$`,"iu").test(a[0]??"")){const[P,...N]=a,H=(N.length>0?N:["7"]).map(te=>Number(te.replace(/\s*s(?:ec(?:onds?)?)?$/iu,"")));return H.some(te=>!Number.isFinite(te)||te<=0)?{ok:!1,message:"Split durations must be positive seconds."}:await cn({sourceReference:pr(P),cutPointsSeconds:bl(H)},void 0,o)}if(l==="/rough-cut")return await Yd("slash",o);if(l==="/sound-effects")return await Zd("slash",o);if(l==="/generate-cell"){if(!c||a.length!==1)return{ok:!1,message:"Usage: /generate-cell @cell-id"};const P=pr(a[0]),N=c.cells.find(H=>H.id.toLowerCase()===P||W(H.slot).slice(1).toLowerCase()===P);return!N||!Bi(N)?{ok:!1,message:"Choose a configured generation cell"}:await Kr(N.id,"slash",o)}if(l==="/arrange-videos-column"||l==="/arrange-videos-row"){const P=$?.slot??Ge;return P?await qd(l==="/arrange-videos-column"?"column":"row",P,o):{ok:!1,message:"Select a cell to anchor the arrangement"}}if(l==="/group-images"){const P=$?.slot??Ge;return P?await Ga(P,o):{ok:!1,message:"Select a cell to anchor the grouping"}}if(l==="/track-add"){const P=Gg(a);return P.ok?await eu(P.kind,P.name,o):P}if(l==="/track-remove"){const P=sw(J,a[0]);return!P||a.length!==1?{ok:!1,message:"Usage: /track-remove @track-id"}:await tu(P.trackId,o)}if(l==="/export-sequence"||l==="/export"&&a.some(P=>P==="@sequence-main"||P.startsWith("--")||P===`@${J?.sequenceId}`)){if(!J)return{ok:!1,message:"Load the primary sequence first."};const P=Ug(a,J.sequenceId);if(!P.ok)return P;const{orientation:N,captions:H}=P,te=Ke(await w("get_primary_sequence",{book_id:i},{chat:o}));if(!te)return{ok:!1,message:"Load the primary sequence first."};Ee(te);const de=await w("plan_sequence_export",{book_id:i,source_surface:"slash",actor:"videobook-user",sequence_revision:te.revision,orientation:N,captions:H},{chat:o}),pe=D(de);if(pe?.kind==="invalid-export"){const He=D(pe.validation);return{ok:!1,message:(Array.isArray(He?.errors)?He.errors.map(Oe=>_(D(Oe)?.message)).filter(Boolean):[]).join(" · ")||"Export validation failed"}}return await Xt(ft(de),o)}const A=Wg(l,a,{sequence:J,assets:B,mentionAssets:se});if(A.handled)return A.ok?await Ja(A.request,"slash",o):A;const y=Dl(In,l,d);if(!y)return{ok:!1,message:`Unknown command: ${l}`};if(S?.handler.kind==="ui"){const P=y.command==="/post"?Fb(d):mt(d,y.params),N=await bi(S,P,o);if(N)return N}if(y.uiAction==="switch_book"){const P=y.command.slice(1),N=x.find(te=>te.name.toLowerCase()===P.toLowerCase());if(!N)return{ok:!1,message:`Book not found: ${P}`};const H=await Na(N.bookId);return H.ok?{ok:!0,message:`Opened ${N.name}`}:{ok:!1,message:H.error}}if(y.uiAction==="open_projects"){const P=await Co();return P.ok?{ok:!0,message:"Project selector opened"}:{ok:!1,message:P.error}}if(y.uiAction==="open_notebook")return tt("notebook"),{ok:!0,message:"Notebook opened"};if(y.uiAction==="x_connect")return tt("settings"),ln(),await ns();if(y.uiAction==="open_provider_keys")return tt("settings"),await ln(),{ok:!0,message:"Settings opened"};if(y.uiAction==="open_music_video"){if(!J)return{ok:!1,message:"Load the primary sequence first."};const P=mt(d,y.params),N=_(P.audio_ref),H=zg(N,B);if(!H.ok)return H;const te=H.asset,de=xt(),pe=document.activeElement instanceof HTMLElement&&document.activeElement!==document.body?document.activeElement:document.querySelector('[aria-label="Videobook command input"]');return M(o,()=>No(null)),Tn(null),wt.load(),Ue({key:de,audioArtifactId:te.artifactId,returnFocus:pe,setup:{status:"loading"}}),no("action")&&me(!0),Xa(de,te.artifactId,J,o).catch(()=>{}),{ok:!0,message:`Music-video editor opened for ${te.label}`}}if(y.uiAction==="open_alive_captions"){const P=mt(d,y.params),N=Bg(_(P.asset_ref),B);if(!N.ok)return N;const H=N.asset,te=xt(),de=document.activeElement instanceof HTMLElement&&document.activeElement!==document.body?document.activeElement:document.querySelector('[aria-label="Videobook command input"]');return M(o,()=>No(null)),Tn(null),Ue(null),Er({key:te,asset:{artifactId:H.artifactId,label:H.label,mediaUrl:H.mediaUrl,width:H.width,height:H.height,fps:H.fps},returnFocus:de,state:{status:"loading"}}),si(te,H.artifactId,!1,o),{ok:!0,message:`Alive captions opened for ${H.label}`}}if(y.uiAction==="speak_preview"){const P=mt(d,y.params),N=Hg({command:y.command,text:_(P.text)??"",voiceId:t?.speakVoiceId,hasNotebook:!!c});return N.kind==="prefill"?{ok:!0,message:N.message,nextInput:N.nextInput,selectInput:!1}:N.kind==="error"?{ok:!1,message:N.message}:await Od(N.text,N.voiceId,o)}if(y.uiAction==="open_cold_open"){const P=mt(d,y.params);return ss(_(P.asset_ref)??void 0,o)}if(y.uiAction==="open_post_dropbox"||y.uiAction==="open_post_icloud")return cs(u||void 0,y.uiAction==="open_post_dropbox"?"dropbox":"icloud",o);if(y.uiAction==="open_watermark"){const P=mt(d,y.params),N=kl(_(P.asset_ref)??void 0,$,B,new Map(se.map(H=>[H.artifactId,H.cellAddress])));return N.ok?(Ba(N.artifactId,N.label,void 0,o),pt(`Watermark review ready for ${N.label}`)):{ok:!1,message:N.message}}if(!y.mcpTool)return{ok:!1,message:`${y.command} is available from its workspace.`};if(y.mcpTool.tool==="download_video"&&!c)return{ok:!1,message:"Open a notebook before downloading media."};const R=mt(d,y.params),V={...Ob(y.mcpTool.adapter,R),...y.mcpTool.injectParams??{}};if(y.mcpTool.autoInject?.includes("book_id")&&(V.book_id=i),y.mcpTool.autoInject?.includes("notebook_id")&&c&&(V.notebook_id=c.id),S&&S.confirmation!=="none")return await Ce(S.id,V,void 0,void 0,o),{ok:!0,message:"Review the action before running it"};const X=await w(y.mcpTool.tool,V,{chat:o});return await gi(y.mcpTool.tool,X,V,y.command,o)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},vu=async(e,t)=>{const o=qe;if(e.handler.kind!=="tool"){if(e.handler.kind==="ui"&&e.handler.action==="open_actions")return await Ce(),{message:"Actions opened"};const a=await bi(e,t);if(a){if(!a.ok)throw new Error(a.message);return Xe(p=>p===o?null:p),{message:a.message}}const l=Object.keys(e.inputSchema.properties??{}).map(p=>t[p]).filter(p=>p!=null).map(p=>Array.isArray(p)?p.join(" "):String(p)).join(" "),u=e.command==="/export-sequence"?`/export-sequence --aspect ${String(t.aspect??"16:9")} --captions ${String(t.captions??"burned")}`:`${e.command}${l?` ${l}`:""}`,d=await fs(u);if(!d.ok)throw new Error(d.message);return Xe(p=>p===o?null:p),{message:d.message}}const n=e.handler.tool;if(n==="delete_asset"&&t.forget===!0){const a=B.find(u=>u.artifactId===t.asset_id);if(!a)throw new Error("Choose media from the current project.");const l=await Cd({...a,errorMessage:null,lastUsedAt:null,owningBookId:i,owningBookName:co?.name??i},!0);if(!l.ok)throw new Error(l.message);return Xe(null),{message:l.message}}if(n==="create_book"||n==="rename_book"||n==="delete_book"){const a=n==="create_book"?await La(String(t.name??"")):n==="rename_book"?await Fa(String(t.book_id??i),String(t.name??"")):await Da(String(t.book_id??i),String(t.confirm_name??""));if(!a.ok)throw new Error(a.error);return{message:`${e.title} complete`}}const r=await w(n,t);if(D(r)?.kind==="chat-action-plan"){const a=await Kn(Ts(r),String(t.prompt??""));if(!a.ok)throw new Error(a.message);return Xe(null),{message:a.message}}if(n==="get_notebook"&&typeof t.notebook_id=="string")return await F(String(t.book_id??i),t.notebook_id),Ao("notebook"),Xe(null),{message:"Notebook opened"};if(D(r)?.planVersion===1&&Array.isArray(D(r)?.stages)){const a=await Xt(ft(r));if(!a.ok)throw new Error(a.message);return Xe(null),{message:a.message}}const s=await gi(n,r,t,e.title);if(!s.ok)throw new Error(s.message);return{message:s.message,value:r}},yu=async(e,t)=>{if(e.confirmation==="generation"&&e.handler.kind==="tool"){const o=D(await w("estimate_cost",{calls:[{tool_name:e.handler.tool,input:t}]})),n=D(o?.estimate),r=Array.isArray(n?.warnings)?n.warnings.filter(u=>typeof u=="string"):[],s=typeof n?.usd=="number"?n.usd:null,a=Gi(r);return{cost:s!==null&&s>0&&(r.length===0||a)?`Estimated cost: $${s.toFixed(4)}`:"Cost estimate unavailable",message:`This action may send your prompt and selected media to a generation provider and incur charges.${r.length?` ${r.join(" ")}`:""} Confirm to start.`}}return{message:e.confirmation==="external"?`${e.title} sends the selected content outside this workspace. Review the destination and content before confirming.`:`${e.title} changes or removes the selected content. Review the target and values before confirming.`}},Iu=async(e,t,o)=>{if(t?.action){const r=Et.find(l=>l.id===t.action?.id);if(!r)return{ok:!1,message:"Reload Actions and choose the command again.",nextInput:e};if(r.handler.kind==="ui"&&(r.handler.action==="open_post_dropbox"||r.handler.action==="open_post_icloud")){const l=e.trim().slice(r.command.length).trim();return cs(l||void 0,r.handler.action==="open_post_dropbox"?"dropbox":"icloud",o)}if(r.handler.kind==="tool"&&r.handler.tool==="transcribe"){const l=or([r],[]).find(S=>S.command===r.command),u=ar(e.trim().slice(r.command.length).trim(),Uo),d=l?mt(u,l.params):{},p=_(d.asset_id)?.trim(),v=_(t.action.values?.asset_id)?.trim();return sn({assetRef:p||v||void 0,languageCode:_(t.action.values?.language_code)??"",diarize:typeof t.action.values?.diarize=="boolean"?t.action.values.diarize:!0,tagAudioEvents:typeof t.action.values?.tag_audio_events=="boolean"?t.action.values.tag_audio_events:!0,chat:o})}const s=or([r],[]).find(l=>l.command===r.command),a=ar(e.trim().slice(r.command.length).trim(),Uo);return await Ce(r.id,{...t.action.values,...mt(a,s.params)},void 0,void 0,o),{ok:!0,message:"Action options opened"}}const n=await fs(e,t,o);return qs(e)||e.trim().toLowerCase()==="/cancel"?jr.current?.(gl(e,n)):ua.current?.(e,n.message),n},Cu=async(e,t,o)=>{const n=(e.subjectMap?.subjects??[]).filter(u=>o.subjectIds.includes(u.id)),r=kg(t),s=bg(r,Uo);if(!s.ok)return{ok:!1,message:s.error,nextInput:t,selectInput:!1};if(s.artifactIds.includes(e.asset.artifactId))return{ok:!1,message:"Mention a different image as the replacement.",nextInput:t,selectInput:!1};if(s.artifactIds.length>0||Object.keys(o.replacements).length>0){const u=wg(o.regions,n),d=hg(u,o.replacements,s.artifactIds);if(!d.ok)return{ok:!1,message:d.error,nextInput:t,selectInput:!1};const p=tb(t,r).replace(/\s+/g," ").trim();return await Gn(e,{operation:"replace",subjectIds:n.map(S=>S.id),...p?{prompt:p}:{},regions:vg(u,d.replacements),...o.model?{model:o.model}:{}})?{ok:!0,message:`Region replacement queued for ${u.length} ${u.length===1?"region":"regions"}.`}:{ok:!1,message:"The image replacement was not queued.",nextInput:t,selectInput:!1}}return o.subjectIds.length===0&&o.regions.length===0?t.trim()?await Gn(e,{operation:"whole_image",subjectIds:[],prompt:t,...o.model?{model:o.model}:{}})?{ok:!0,message:"Whole-image edit queued."}:{ok:!1,message:"The whole-image edit was not queued.",nextInput:t,selectInput:!1}:{ok:!1,message:"Describe the whole-image edit first.",nextInput:t,selectInput:!1}:o.subjectIds.length>0&&e.subjectMap?.status!=="ready"?{ok:!1,message:e.subjectMap?.status==="analyzing"?"Wait for people and object analysis to finish before editing.":"Analyze the image before editing subjects, or draw a region to edit.",nextInput:t,selectInput:!1}:await Gn(e,{operation:"edit",subjectIds:n.map(u=>u.id),prompt:t,...o.regions.length>0?{editRegions:o.regions.map(u=>u.box)}:{},...o.model?{model:o.model}:{}})?{ok:!0,message:`Image edit queued for ${o.regions.length+n.length} selected areas.`}:{ok:!1,message:"The image edit was not queued.",nextInput:t,selectInput:!1}},wi=e=>(/^\/(?:apply|cancel)(?:\s|$)/iu.test(e)&&(E||ue||he)||((E||ue||he)&&Fe(),Z(null),Le(null),kt(null),jo(null),Xe(null),Y&&Kt(),Do(null)),ma(e)),ms=async(e,t)=>{const o=t?.chat??(qs(e)||e.trim().toLowerCase()==="/cancel"?ma(e):void 0);o?.working();try{const n=await Iu(e,t,o);return o?.finish({...n,...e.trim().toLowerCase()==="/cancel"&&n.ok?{status:"cancelled"}:{}}),n}catch(n){const r={ok:!1,message:n instanceof Error?n.message:String(n)};return o?.finish(r),r}},Eo=e=>{hc(t=>t?.row===e?.row&&t?.column===e?.column?t:e)},hi=(e,t)=>{const o=Oo.current?.screenToFlowPosition({x:e,y:t});if(!o)return null;const n=ug(o,Tt);return n?vt.some(r=>r.row===n.row&&r.column===n.column)?null:n:null},vi=(e,t)=>G?null:hi(e,t),Su=e=>{b!=="notebook"||!Dt(e.dataTransfer)||Fo(!0)},xu=e=>{if(b!=="notebook"||!Dt(e.dataTransfer))return;const t=e.relatedTarget;t instanceof Element&&e.currentTarget.contains(t)||(Fo(!1),Eo(null))},Eu=e=>{Dt(e.dataTransfer)&&e.preventDefault()},Au=e=>{Dt(e.dataTransfer)&&(Fo(!1),Eo(null))},_u=e=>{!Dt(e.dataTransfer)||e.defaultPrevented||(e.preventDefault(),b==="notebook"&&h("Drop one image, video, or audio file on an open grid square","error"))},Ru=e=>{if(!Dt(e.dataTransfer))return;const t=e.relatedTarget;t instanceof Element&&e.currentTarget.contains(t)||Eo(null)},Pu=e=>{if(e.preventDefault(),Dt(e.dataTransfer)){Gt(null),Fo(!0);const o=vi(e.clientX,e.clientY);Eo(o),e.dataTransfer.dropEffect=o?"copy":"none";return}Eo(null);const t=Oo.current?.screenToFlowPosition({x:e.clientX,y:e.clientY});t&&Gt(fl(t))},Mu=e=>{if(e.preventDefault(),Dt(e.dataTransfer)){if(e.stopPropagation(),Gt(null),Fo(!1),Eo(null),G){h("Wait for the current operation to finish","error");return}const n=[...e.dataTransfer.files];if(n.length!==1){h("Drop one image, video, or audio file per square","error");return}const r=vi(e.clientX,e.clientY);if(!r){h("Choose an open grid square for the media file","error");return}ts(r,n[0]);return}const t=e.dataTransfer.getData("application/x-videobook-cell");if(!dg(t))return;const o=Oo.current?.screenToFlowPosition({x:e.clientX,y:e.clientY});Gt(null),es(t,o)},Ao=e=>{gt(null),Vt(null),wo(),z&&zn(),tt(e),e==="settings"&&ln(),e==="jobs"&&i&&F(i,c?.id).catch(t=>{h(t instanceof Error?t.message:String(t),"error")})},Tu={ready:g.state==="ready",states:xr,onFile:(e,t)=>{Wa(e,t)},onFileError:Zo,onOpenLibrary:xo},yi=z?c?.cells.find(e=>e.id===z.cellId):void 0,qt=yi?Ft(yi.type):z?.cellId===null?"all":null,Jn=z?{...z,uploading:z.cellId!==null&&xr[z.cellId]?.operation==="upload",mode:fe.state.mode,reference:fe.state.reference,referenceStartSeconds:fe.state.startSeconds,referenceDurationSeconds:fe.state.durationSeconds,preparingReference:fe.state.preparing,error:fe.state.error??z.error}:null,ju=e=>{ke(t=>t&&{...t,draftQuery:e})},$u=e=>{if(!z||fe.state.mode===e)return;const t=z.cellId;_e.current+=1,fe.lifecycle.changeMode(e),ke(o=>o&&o.cellId===t?{...o,page:e==="text"?o.page:{...mr,total:o.assets.length},error:null,loading:!1,loadingMore:!1,preparingIndex:!1}:o),e==="text"&&Ct(t,z.draftQuery,0,!1,{mode:e,reference:null,referenceStartSeconds:"0",referenceDurationSeconds:""})},qu=async e=>{if(!z||fe.state.mode==="text"||!i)return;const t=z;_e.current+=1;const o=fe.state.mode;ke(r=>r&&r.cellId===t.cellId?{...r,error:null,loading:!1,loadingMore:!1,preparingIndex:!1}:r);const n=await fe.lifecycle.prepare(o,()=>eg(e,i,qg(o)));if(n.status==="error"){h(n.error,"error");return}n.status!=="stale"&&await Ct(t.cellId,"",0,!1,{mode:n.mode,reference:n.reference,referenceStartSeconds:"0",referenceDurationSeconds:""})},Nu=async e=>{if(!z)return;const t=z;_e.current+=1;const o=e.type==="image"?"image-reverse":"video-reverse";ke(r=>r&&r.cellId===t.cellId?{...r,error:null,loading:!1,loadingMore:!1,preparingIndex:!1}:r);const n=await fe.lifecycle.prepare(o,()=>Zp(w,{sourceBookId:e.owningBookId,sourceArtifactId:e.artifactId,mode:o,previewUrl:o==="image-reverse"?e.thumbnailUrl??e.mediaUrl:e.mediaUrl}));if(n.status==="error"){h(n.error,"error");return}n.status!=="stale"&&await Ct(t.cellId,"",0,!1,{mode:n.mode,reference:n.reference,referenceStartSeconds:"0",referenceDurationSeconds:""})},Lu=()=>{z&&(_e.current+=1,fe.lifecycle.clearReference(),ke(e=>e&&{...e,error:null,loading:!1,loadingMore:!1,preparingIndex:!1}))},Fu=async()=>{if(!z||!qt||qt==="audio")return;const e=z,t=++_e.current;ke(o=>o&&{...o,preparingIndex:!0,error:null});try{const o=await Yp({start:()=>w("repair_library_search_indexes",{kinds:qt==="all"?["image","video"]:[qt]}),listJobs:(s,a)=>w("list_jobs",{book_id:s,job_ids:a}),isCancelled:()=>_e.current!==t});if(_e.current!==t)return;const n=_e.current+1;if(await Ct(e.cellId,e.query,0,!1),_e.current!==n)return;if((ie(o?.failed)??0)>0){const s=Array.isArray(o?.failures)?o.failures:[],a=_(D(s[0])?.message),l=`Some media could not be indexed.${a?` ${a}`:""}`;ke(u=>u&&{...u,error:l}),h(l,"error")}else h(`Indexed ${ie(o?.indexed)??0} media assets for Similar search`)}catch(o){if(_e.current!==t)return;const n=o instanceof Error?o.message:String(o);ke(r=>r&&{...r,preparingIndex:!1,error:n}),h(n,"error")}},Du=()=>{z&&(fe.lifecycle.clearError(),Ct(z.cellId,z.draftQuery,0,!1))},Ou=()=>{z&&Ct(z.cellId,z.query,z.page.offset+z.page.limit,!0)},Vu=e=>{if(!z)return;const t=Xp(z.tagFilters,e);Qp(t,z.tagFilters)||Ct(z.cellId,z.query,0,!1,void 0,t)},Gu=()=>{!z||z.tagFilters.length===0||Ct(z.cellId,z.query,0,!1,void 0,[])},Uu=async e=>{if(!z||g.state!=="ready")return;const t=z.cellId;try{const o=await w("suggest_asset_tags",{book_id:i,...e.trim()?{prefix:e.trim()}:{},limit:20},{background:!0}),n=Array.isArray(o?.suggestions)?o.suggestions.flatMap(r=>{const s=r;return typeof s.facet=="string"&&typeof s.key=="string"&&typeof s.label=="string"?[{facet:s.facet,key:s.key,label:s.label,assets:Number(s.assets)||0}]:[]}):[];ke(r=>r&&r.cellId===t?{...r,tagSuggestions:n}:r)}catch{}},Qt=e=>{if(za(e)&&g.state==="ready"){xo(e);return}Z(e),Le(null),kt(null),no("selection")&&me(!0)},Ii=e=>{Z(e),kt(null),Le(e),no("selection")&&me(!0);const t=c?.cells.find(o=>o.id===e);t?.outputArtifactId&&!oo(t.type)&&Si(e,t.outputArtifactId)},Ci=(e,t)=>{const o=c?.cells.find(n=>n.id===e);if(o&&!oo(o.type)){Ii(e);return}Z(e),Le(null),kt(e),no("selection")&&me(!0),Si(e,t)},Si=(e,t)=>{if(!i){_n({cellId:e,assetId:t,loading:!1,error:"Book is unavailable",revisions:[]});return}_n({cellId:e,assetId:t,loading:!0,error:null,revisions:[]}),w("asset_history",{asset_id:t,book_id:i,limit:20},{background:!0}).then(o=>{const n=Ng(o);_n(r=>r?.cellId===e&&r.assetId===t?{cellId:e,assetId:t,loading:!1,error:null,revisions:n}:r)}).catch(o=>{_n(n=>n?.cellId===e&&n.assetId===t?{cellId:e,assetId:t,loading:!1,error:o instanceof Error?o.message:String(o),revisions:[]}:n)})},ee=Ht?c?.cells.find(e=>e.id===Ht)??null:null,Re=Ht?Mt.find(e=>e.id===Ht)??null:null,_o=Ye?.target.kind==="slot"?Ye.target.slot:null,ps=Re?gp({type:Re.data.kind,model:Re.data.model,operation:Re.data.operation,outputArtifactId:Re.data.outputArtifactId,tool:Re.data.tool},Re.data.status):null,Wu=ee?Ft(ee.type):null,zu=!!(ee&&Re&&Wu&&kp(ee.type,ee.outputArtifactId,Re.data.targetConnectionCount??0)),De=Re?.data.asset&&Re.data.asset.type!=="audio"&&(Re.data.asset.mediaUrl||Re.data.asset.thumbnailUrl)?Re.data.asset:null,Xn=ee?.outputArtifactId&&Re?.data.asset&&Os(Re.data.asset.type)?ee.outputArtifactId:null,Bu=!!(c&&ee&&Xn&&ee.slot.row+1<gn.maximumRowCount&&!vt.some(e=>e.row===ee.slot.row+1&&e.column===ee.slot.column)),gs=Me===Ht?dd:null,Hu=ee&&c&&ee.type!=="goal"?["generate_video","generate_image"].filter(e=>{try{return Bl({actions:Qe,cellId:`context-menu-${e}`,cellType:e,document:c,lastWorkSlot:Ge,sourceCellId:ee.id}),!0}catch{return!1}}):[],Be=[];if(ee&&Re){if(ee.type==="post"){const e=G||g.state!=="ready";Be.push({id:"save-iphone",label:"Save to iPhone",icon:"upload",disabled:e},{id:"upload-dropbox",label:"Upload to Dropbox",icon:"upload",disabled:e})}Be.push({id:"inspect",label:ee.type==="goal"?"Open goal":"Edit cell",icon:"inspect"}),ps&&Be.push({id:"run",label:bp(ee.type,ps.label),icon:"run",disabled:G||ps.disabled}),zu&&Be.push({id:"library",label:"Choose media",icon:"library",disabled:G}),De&&ee.type!=="post"&&["video","image","final"].includes(De.type)&&Be.push({id:"create-post",label:"Create Post",icon:"inspect",disabled:G||g.state!=="ready"}),De&&Be.push({id:"media",label:"Open media",icon:"media"}),De&&(De.type==="video"||De.type==="final")&&(Be.push({id:"cold-open",label:"Edit cold open",icon:"split",disabled:G||g.state!=="ready"||!De.mediaUrl}),Be.push({id:"download",label:"Download video",icon:"download",disabled:G||g.state!=="ready"||!De.mediaUrl}),Be.push({id:"extract_frame",label:"Extract frame",icon:"extract-frame",disabled:G}));for(const e of Hu){const t=e==="generate_video";Be.push({id:e,label:t?"Generate video":"Generate image",icon:t?"generate-video":"generate-image",disabled:G})}Xn&&Be.push({id:"duplicate",label:"Duplicate",icon:"duplicate",disabled:G||!Bu}),gs&&Be.push({id:"split",label:"Split video",icon:"split",disabled:G})}const Qn=[];Ma.size>0&&Qn.push({id:"group_images",label:"Group images here",icon:"group-images",disabled:G});const Ku=e=>{_o&&e==="group_images"&&Ga(_o)},Ju=async()=>{if(!(!Xn||!i||!c)){T(!0);try{const e=D(await w("duplicate_asset",{asset_id:Xn,book_id:i,notebook_id:c.id})),t=_(e?.cell_id),o=_(e?.address);if(!t||!o)throw new Error("The server did not return the duplicated notebook cell");await F(i,c.id),Z(t),ae(),h(`Duplicated as ${o}`)}catch(e){h(e instanceof Error?e.message:String(e),"error")}finally{T(!1)}}},Xu=async e=>{if(!i||!c||!ee)return;const t=c.id,o=ee.id;T(!0);try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:t}));if(!n)throw new Error("The server returned an invalid notebook");const r=Bl({actions:Qe,cellId:xt(),cellType:e,document:n,lastWorkSlot:Ge,sourceCellId:o}),s=await vl({bookId:i,callTool:w,document:n,draft:r,...n.revision?{expectedRevision:n.revision}:{}});Ae(r.cell.slot);const a=await F(i,t);Qt(s.cellId),Yo(s.cellId,void 0,a),ao(s.cellId),h(`Added ${s.cellAddress} ${e==="generate_video"?"video":"image"} generation from ${s.sourceAddresses[0]}`)}catch(n){h(n instanceof Error?n.message:String(n),"error")}finally{T(!1)}},Qu=async()=>{if(!i||G||g.state!=="ready"||!De?.mediaUrl)return;const e=De.artifactId;T(!0);try{const t=await Xg(w,"download",i,e);Q.current.bookId===i&&h(t)}catch(t){Q.current.bookId===i&&h(t instanceof Error?t.message:String(t),"error")}finally{Q.current.bookId===i&&me(!0),T(!1)}},Yu=e=>{if(ee){if(e==="save-iphone"||e==="upload-dropbox"){const t=ls(ee.id,e==="upload-dropbox"?"dropbox":"icloud");t.ok||h(t.message,"error");return}if(e==="create-post"){Oa(ee.id);return}if(e==="inspect"){Qt(ee.id);return}if(e==="run"){on(ee.id);return}if(e==="library"){xo(ee.id);return}if(e==="cold-open"&&De){const t=ss(De.artifactId);t.ok||h(t.message,"error");return}if(e==="download"){Qu();return}if(e==="media"||e==="extract_frame"){De&&Vn(ee,De,Ye?.returnFocus??null);return}if(e==="duplicate"){Ju();return}if(e==="generate_video"||e==="generate_image"){Xu(e);return}if(e==="split"&&gs){cn({sourceReference:gs.source.id,cutPointsSeconds:[]}).then(t=>{t.ok||h(t.message,"error")});return}}},Zu=()=>{ee&&So([ee])},ef=async e=>{if(!i||!c)return;const t=c.cells.find(a=>a.id===e);if(!t)return;const o=ig(t,c.cells,c.edges),n=lg({address:W(t.slot),error:Mt.find(a=>a.id===e)?.data.statusError??"the provider rejected the request",mediaLabel:cg(t.type),producerAddress:o?W(o.slot):null,provider:o?.provider??t.provider??null,model:o?.model??t.model??null});me(!0);const r=wi(n),s=await ms(n,{chat:r});s.ok||h(s.message,"error")},tf=async e=>{if(!i||!c||G||g.state!=="ready")return;const t=Mt.find(n=>n.id===e)?.data.statusError;if(!sg(t))return;const o=ag(c,e);if(!o){h("The generator for this failed output is no longer available","error");return}await on(o.id,void 0,void 0,e)},of={ready:!G&&g.state==="ready",deleteCell:async e=>{const t=c?.cells.find(o=>o.id===e);t&&await So([t],{confirm:!1})},repairCell:ef,retryCell:tf},un=Y?.asset.type==="image"?Y:null,xi=m.useMemo(()=>un?se.filter(e=>e.type.toLowerCase()==="image"&&e.artifactId!==un.asset.artifactId):[],[se,un]),nf=m.useMemo(()=>xi.map(e=>({artifactId:e.artifactId,address:e.cellAddress,label:e.cellAddress,thumbnailUrl:e.thumbnailUrl??e.mediaUrl})),[xi]),Yn=un?`image-edit:${un.key}`:`chat:${i}`,Ro=Cn?.bookId===i&&Cn.session===Yn?Cn:null,rf=hr?.bookId===i&&hr.session===Yn?hr:null,Ei=Ne?.turnId!==void 0&&Ne.turnId===fa.at(-1)?.id,Ai=!!(Ro&&(Ne||Y)),ks=!Qo&&!ve&&!it,sf=e=>{if(!U)return;let t=U,o=!1;for(const n of e){if(n.kind==="prompt"){t=tr(t,n.prompt);continue}if(n.kind==="model"){const r=Wo.find(s=>s.id===n.actionId);if(!r)continue;t=Xi(t,r,bt),o=!0;continue}t=xs(t,n.name,n.value),o=!0}yt(t,o)},af=async e=>{const t=E?.kind==="generation"&&U?{kind:"generation",action:U.action,models:Wo}:E?.kind==="chain-step"?{kind:"chain-step"}:E?.kind==="transcribe"?{kind:"transcribe"}:E||ue||he?{kind:"other"}:{kind:"none"},o=Ig(e,t);return o.kind==="refused"?o.outcome:o.kind==="revise"?(sf(o.edits),{status:"review",message:"The review on screen is updated. It is still waiting for apply or cancel."}):gl(o.input,await ms(o.input))},Yt=wp({bookId:i,notebookId:c?.id,scope:Yn,available:ks&&g.state==="ready"&&!!i&&!Y&&!Ne&&!ve,disabled:G||!!(he||ue||E),onUserTurn:()=>{he||ue||E||(ka.current=ga(),Z(null),Le(null),kt(null))},onAction:async(e,t)=>{const o=ka.current??ga(),n=()=>t()&&o.isCurrent();if(!n())return{status:"cancelled",message:"A newer message replaced this request."};if(G||E||ue||he)return{status:"failed",message:"Finish the current command or use Apply or Cancel on screen first."};const r=Ts(e.plan);if(r.bookId!==i)return{status:"cancelled",message:"The project changed. Repeat the command here."};const s=await Kn(r,e.prompt,n,o);return n()?(h(s.message,s.ok?"info":"error"),{status:s.ok?s.nextInput?.startsWith("/apply")?"review":/queued|started|running|processing/i.test(s.message)?"queued":"completed":"failed",message:s.message}):{status:"cancelled",message:"Workspace changed. Check the previous project for accepted work."}},onReviewCommand:af});m.useLayoutEffect(()=>{jr.current=Yt.reportOutcome,ua.current=Yt.shareTypedTurn,$r.current=Yt.active},[Yt.active,Yt.reportOutcome,Yt.shareTypedTurn]),hp(`${b}:${i}:${c?.id??""}`,ks&&g.state==="ready"&&!G&&(!!i||!!Ro));const lf=()=>{Y||Kc()},_i=(()=>{if(he){const s=he,a=s.includeQr&&s.includeHandle?"Add handle and QR to the video":s.includeQr?"Add a QR code to the video":"Add a handle to the video";return C.jsx(ot,{kind:"watermark",ariaLabel:"Watermark review",tag:"WATERMARK · CHAT",title:a,address:s.targetLabel,effect:{label:"Rebuilds playable proxy",tone:"default"},validation:yp({...s,handle:s.identities[s.platform].handle}),busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Wb,{busy:G,state:s,onChange:({handle:l,...u})=>{nl(i,s.platform,{handle:l,...u}),Te(d=>d&&{...d,...u,identities:l===void 0?d.identities:{...d.identities,[d.platform]:{...d.identities[d.platform],handle:l}},error:null})},onMediaMetadata:l=>Te(u=>u&&{...u,...u.durationSeconds===null?vp(u,l.durationSeconds):{},durationSeconds:l.durationSeconds,width:l.width,height:l.height})})})}if(ue){const s=ue.plan,a=Object.values(ue.previews),l=a.reduce((p,v)=>p+v.warnings.length,0),u=`${s.stages.length} stage${s.stages.length===1?"":"s"}`,d=l>0?` · ${l} warning${l===1?"":"s"}`:"";return C.jsx(ot,{kind:"plan",ariaLabel:"Command plan review",tag:`PLAN · ${s.sourceSurface.toUpperCase()}`,title:s.summary,effect:{label:`${u}${d}`,tone:l>0?"warning":"default"},validation:Ip({suggestions:s.suggestions,previews:a}),busy:G,applyFormId:nt,onCancel:Fe,secondaryActions:qr?C.jsxs("button",{type:"button",className:"confirm-sheet-secondary",disabled:G,onClick:()=>{Qd()},children:[C.jsx(db,{size:13,"aria-hidden":"true"}),"Restore last edit"]}):null,children:C.jsx(Bk,{busy:G,plan:s,previews:ue.previews,onToggleSuggestion:p=>{Jd(p)}})})}if(!E)return null;if(E.kind==="transcribe"){const s=E,a=new Map(se.map(p=>[p.artifactId,p.cellAddress])),l=Cp(B,a),u=l.find(p=>p.artifactId===s.assetId)??null,d=p=>{O(v=>v?.kind==="transcribe"?{...v,...p}:v)};return C.jsx(ot,{kind:"transcribe",ariaLabel:"Transcribe review",tag:"TRANSCRIBE · CHAT",title:u?`Transcribe ${u.label}`:"Transcribe a clip",address:u?.label??null,effect:{label:"Queues 1 transcription",tone:"default"},validation:rl({assetId:s.assetId,languageCode:s.languageCode}),busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Hk,{busy:G,clip:u,choices:l,languageCode:s.languageCode,diarize:s.diarize,tagAudioEvents:s.tagAudioEvents,estimateUsd:s.estimateUsd,estimateLoading:s.estimateLoading,estimateUnavailable:s.estimateUnavailable,onClipChange:p=>{d({assetId:p,estimateUsd:null,estimateLoading:p!==null,estimateUnavailable:!1}),p?Un(p,s.languageCode,s.diarize,s.tagAudioEvents):To.current+=1},onLanguageChange:p=>d({languageCode:p}),onDiarizeChange:p=>{d({diarize:p,estimateUsd:null,estimateLoading:s.assetId!==null,estimateUnavailable:!1}),s.assetId&&Un(s.assetId,s.languageCode,p,s.tagAudioEvents)},onTagAudioEventsChange:p=>{d({tagAudioEvents:p,estimateUsd:null,estimateLoading:s.assetId!==null,estimateUnavailable:!1}),s.assetId&&Un(s.assetId,s.languageCode,s.diarize,p)}})})}if(E.kind==="generation"){const s=E,a=zo[0];return C.jsx(ot,{kind:"generation",ariaLabel:"Generation action review",tag:"GENERATION · CHAT",title:s.summary,address:a?`@${a.address}`:null,effect:{label:"Queues 1 job · new cell",tone:"default"},validation:Sp({prompt:s.draft.cell.prompt,previewLoading:s.previewLoading,previewError:s.previewError,settingsError:Ap(s.draft.action.model,sl(s.draft),zo),previewStale:s.previewStale,promptLeaks:Ep(s.preview).promptLeaks,estimateUnknown:xp(s.preview).unknown}),busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Kk,{actions:Wo,busy:G,draft:s.draft,modes:jc,preview:s.preview,previewError:s.previewError,previewLoading:s.previewLoading,previewStale:s.previewStale,sources:zo,sourceOptions:$c,voiceCatalog:Bn,promptHistory:ed,onActionChange:td,onAddSource:ad,onModeChange:od,onPromptChange:Pa,onRefreshPreview:rd,onRemoveSource:id,onSelectSource:sd,onSettingChange:nd})})}if(E.kind==="post-delivery"){const s=E.review,a=dn.find(p=>p.id===s.postId)??null,l=c?.cells.find(p=>p.id===s.postId),u=l?.outputArtifactId?re.get(l.outputArtifactId)??null:null,d=s.destination==="icloud";return C.jsx(ot,{kind:"post-delivery",ariaLabel:"Post delivery",tag:"DELIVER",title:d?"Save to iPhone":"Upload to Dropbox",address:a?.address??null,effect:{label:d?"iCloud · shared folder":"Leaves workspace · private",tone:d?"default":"warning"},validation:al(a,s),busy:G,busyLabel:d?"Saving to iPhone…":"Uploading to Dropbox…",applyLabel:"Upload",applyFormId:nt,onCancel:Fe,children:a&&C.jsx(Jk,{post:a,asset:u,review:s,busy:G,onCopyChange:p=>ut({copy:p}),onLanguage:p=>pu(a,s,p),onRegen:()=>gu(a,s),onFolderChange:p=>ut(d?{icloudFolder:p}:{dropboxFolder:p}),onDestination:ku,onConnect:()=>{mu()},onCheckConnection:()=>{is()},onOpenPost:()=>Qt(a.id),onLink:async p=>{await w("link_post",{book_id:s.bookId,post_cell_id:a.id,...p}),await F(s.bookId,s.notebookId),Fe()}})})}if(E.kind==="cold-open"){const s=E.review,a=s.suggestion;return C.jsx(ot,{kind:"cold-open",ariaLabel:"Cold-open review",tag:"COLD OPEN",title:"Highlight, then the full clip",address:s.label,effect:{label:"New video copy",tone:"default"},validation:{blocking:a?_p(a.startSeconds,a.endSeconds,a.durationSeconds):null,notice:null},busy:G,busyLabel:a?"Creating copy…":"Finding highlight…",applyLabel:a?"Create copy":"Find highlight",applyFormId:nt,onCancel:Fe,children:C.jsx(Xk,{review:s,disabled:G,onChange:(l,u)=>O(d=>d?.kind==="cold-open"&&d.review.suggestion?{...d,review:{...d.review,requestId:xt(),suggestion:{...d.review.suggestion,startSeconds:l,endSeconds:u}}}:d)})})}if(E.kind==="split"&&$a){const s=$a,a=Rp({cutPointsSeconds:s.cutPointsSeconds,sourceDurationSeconds:s.sourceDurationSeconds});return C.jsx(ot,{kind:"split",ariaLabel:"Video split review",tag:"SPLIT VIDEO · CHAT",title:Mp({pieces:a,selectedIndex:s.selectedIndex}),address:s.sourceLabel,effect:{label:s.outputMode==="all"?`${a.length} new clip${a.length===1?"":"s"} · source preserved`:"New clip · source preserved",tone:"default"},validation:Pp({availableEmptyCells:s.availableEmptyCells,cutPointsSeconds:s.cutPointsSeconds,outputMode:s.outputMode,sourceDurationSeconds:s.sourceDurationSeconds}),busy:G,applyLabel:"Apply split",applyFormId:nt,hints:C.jsxs("span",{children:[C.jsx("kbd",{children:"← →"})," 0.1s · ",C.jsx("kbd",{children:"⇧← →"})," 1s · ",C.jsx("kbd",{children:"⌥← →"})," 0.01s on the focused bound · ",C.jsx("kbd",{children:"↵"})," apply · ",C.jsx("kbd",{children:"Esc"})," cancel"]}),onCancel:Fe,children:C.jsx(Qk,{cutPointsSeconds:s.cutPointsSeconds,mediaUrl:s.mediaUrl,outputMode:s.outputMode,selectedIndex:s.selectedIndex,sourceDurationSeconds:s.sourceDurationSeconds,sourceFps:s.sourceFps,onChange:Zc})})}if(E.kind==="routed"){const s=E.plan,a=Tc,l=a?.settings.find(d=>d.label==="Source")?.value,u=`CHAT · ${s.routedTool.toUpperCase()}`;return uo?C.jsx(ot,{kind:"post",ariaLabel:"Chat action review",tag:u,title:a?.title??"Post to X",address:uo.sourceLabel,effect:a?.effect??null,validation:uo.validation,busy:G,busyLabel:"Posting…",applyLabel:"Post to X",applyFormId:nt,onCancel:Fe,children:C.jsx(Yk,{asset:uo.asset,busy:G,draft:uo.draft,prompt:s.prompt,settings:a?.settings??[],sourceLabel:uo.sourceLabel,threadReview:E.xPostReview,connection:$o,onChange:Jc,onConnect:()=>{ns()},onThreadOptionsChange:Xc,onThreadCreditsChange:Yc,onThreadPromptChange:Qc})}):C.jsx(ot,{kind:"routed",ariaLabel:"Chat action review",tag:u,title:a?.title??s.summary,address:l?.startsWith("@")?l:null,effect:a?.effect??null,validation:_s,busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Ml,{prompt:s.prompt,settings:a?.settings??[],speedPreview:ha})})}if(E.kind==="chain-step"){const s=Tp(E.review,E.remaining);return C.jsx(ot,{kind:"routed",ariaLabel:"Chain step review",tag:`CHAIN · ${E.review.tool.toUpperCase()}`,title:s.title,address:E.review.address,effect:s.effect,validation:_s,busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Ml,{prompt:s.postText??"",settings:s.settings,speedPreview:null})})}const e=E,t=e.kind==="notebook"?e.plan.summary:e.summary,o=e.kind==="notebook"?e.plan.reason:e.reason,n=e.kind==="notebook"?`${e.plan.action.kind} notebook cell`:e.kind==="split"?"Split video":e.command.frameMode==="time"?`Extract frame at ${e.command.timestampSeconds??0}s`:`Extract ${e.command.frameMode} frame`,r=e.kind==="notebook"?"Edits the notebook graph":e.kind==="frame"?"New image cell":"New clips · source preserved";return C.jsx(ot,{kind:e.kind,ariaLabel:"Chat action review",tag:"NOTEBOOK · CHAT",title:t,effect:{label:r,tone:"default"},validation:_s,busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Zk,{kindLabel:e.kind.toUpperCase(),reason:o,stageTitle:n})})})(),fn=m.useMemo(()=>{const e=B.map(a=>{const l=c?.cells.find(u=>u.outputArtifactId===a.artifactId);return{value:a.artifactId,label:l?`${W(l.slot)} · ${a.label}`:a.label,detail:a.type}}),t=c?.cells.map(a=>({value:a.id,label:`${W(a.slot)} · ${a.label??a.type}`}))??[],o=J?.tracks.map(a=>({value:a.trackId,label:a.name,detail:a.kind}))??[],n=J?.clips.map(a=>({value:a.clipId,label:`${a.source.kind} · frame ${a.timelineStartFrame}`,detail:J.tracks.find(l=>l.trackId===a.trackId)?.name}))??[],r={book_id:x.map(a=>({value:a.bookId,label:a.name})),notebook_id:c?[{value:c.id,label:c.name}]:[],cell_id:t,cell:t,source_cell_id:t,target_cell_id:t,clip_id:n,clip_ids:n,narration_clip_id:n,track_id:o,track_ids:o,audio_track_id:o,artifact_id:e,artifact_ids:e,artifact_ref:e,asset_id:e,asset_ref:e,source_artifact_id:e};for(const a of["image","audio","video"]){const l=e.filter(u=>u.detail===a||a==="video"&&u.detail==="final");r[`${a}_ref`]=l,r[`${a}_refs`]=l,r[`${a}_artifact_id`]=l,r[`${a}_asset_id`]=l,r[`${a}_asset_ids`]=l}for(const a of["source_asset_id","target_asset_id","first_asset_id","second_asset_id","additional_asset_ids","output_artifact_id","replacement_artifact_id","expected_output_artifact_id","exclude_artifact_ids"])r[a]=e;for(const a of["osg_asset_id","card_asset_id","qr_image_refs","character_image_refs","first_frame_ref","last_frame_ref","end_frame_ref"])r[a]=r.image_ref;return r.motion_video_refs=r.video_ref,r.layer_asset_id=r.audio_ref,r.sound_effect_ref=r.audio_ref,r.source_script_id=e.filter(a=>a.detail==="script"),r.cell_ids=t,r.audio_id=n,r.outgoing_clip_id=n,r.incoming_clip_id=n,r.source_book_id=r.book_id,r.target_book_id=r.book_id,r.edge_id=c?.edges.map(a=>({value:a.id,label:`${t.find(l=>l.value===a.source)?.label??a.source} → ${t.find(l=>l.value===a.target)?.label??a.target} · ${a.targetInput}`}))??[],{bookId:i,notebookId:c?.id,sequenceId:J?.sequenceId,sequenceRevision:J?.revision,cellId:$?.id,assetId:$?.outputArtifactId,choices:r,cellIds:It.map(a=>a.id),assetIds:It.flatMap(a=>a.outputArtifactId?[a.outputArtifactId]:[]),media:Object.fromEntries(B.map(a=>[a.artifactId,{url:a.mediaUrl,type:a.type,width:a.width,height:a.height,objectHash:a.objectHash}]))}},[B,i,x,c,$,It,J]),cf=m.useMemo(()=>jp(In,!!(ue||E||he)),[In,ue,E,he]),bs=(e,t=et.frame)=>{J&&(Z(e),Ue(null),wt.load(),et.seek(t),Tn({bookId:i,cellId:e,initialFrame:t,returnFocus:document.activeElement instanceof HTMLElement?document.activeElement:null}))},Ri=()=>{et.closePicker(),wt.stop(),Tn(null)},ws={sequence:J,assets:B,assembly:Qo?{...et,picker:null}:et,disabled:G||g.state!=="ready",frame:et.frame,onSeek:bs,onPreview:bs,onExport:()=>{fs("/export-sequence").then(e=>{e.ok||h(e.message,"error")})},onRemove:e=>{const t=c?.cells.find(o=>o.id===e);t&&So([t])}},mn=Jn&&(Jn.cellId===null||$?.id===Jn.cellId&&!$.outputArtifactId)?Jn:null,hs=mn&&qt?C.jsx(wf,{disabled:G||g.state!=="ready",state:mn,kind:qt,accept:qt==="all"?Object.values(il).join(","):il[qt],targetBookId:i,onClose:Fd,onMode:$u,onDraftQuery:ju,onSearch:Du,onLoadMore:Ou,onAttach:e=>{Dd(e)},onUpload:e=>{if(mn.cellId){Wa(mn.cellId,e);return}const t=Rs(e);if(!(!t||!c))try{const o=z?.slot??Mo(t,c.cells,Ge);ts(o,e)}catch(o){h(o instanceof Error?o.message:String(o),"error")}},onReferenceFile:e=>{qu(e)},onClearReference:Lu,onReferenceStart:fe.lifecycle.setStartSeconds,onReferenceDuration:fe.lifecycle.setDurationSeconds,onSimilar:e=>{Nu(e)},onRepairIndexes:()=>{Fu()},onToggleTagFilter:Vu,onClearTagFilters:Gu,onTagQuery:e=>{Uu(e)}}):null,df=mn?.cellId===null&&hs?C.jsxs("div",{className:"composer-notebook-dock inspector",children:[C.jsxs("header",{children:[C.jsxs("span",{className:"inspector-cell-title",children:[C.jsx($l,{size:15}),C.jsx("strong",{children:"Library"})]}),C.jsx("div",{className:"inspector-header-actions",children:C.jsx($i,{})})]}),hs]}):null,vs=$?.type==="goal"?Ia.get($.id)??null:null,uf=!Qo&&$?.type==="goal"?vs?C.jsx(ab,{goal:vs,connected:g.state==="ready",onAction:hd,onPreview:vd,onSelectCell:Qt,resolveAsset:e=>re.get(e)??null,onPreviewCell:e=>{const t=c?.cells.find(n=>n.id===e),o=t?.outputArtifactId?re.get(t.outputArtifactId):null;t&&o&&Vn(t,o)}},vs.goalId):C.jsx(ib,{}):null,ys=df??uf??(!Qo&&ce&&$&&$.type!=="timeline"?C.jsxs("div",{className:["composer-notebook-dock","inspector",Sr.has(ce.id)?"inspector-deleting":""].filter(Boolean).join(" "),children:[C.jsxs("header",{children:[C.jsxs("span",{className:"inspector-cell-title",title:Ps(ce.data.kind),children:[C.jsx(hf,{kind:ce.data.kind}),C.jsx("strong",{children:Ps(ce.data.kind)}),C.jsx("code",{className:"inspector-cell-address",children:W($.slot)}),(Yr?.kind==="queued"||Yr?.kind==="generating")&&C.jsx("span",{className:"inspector-generating-badge",role:"status",children:Yr.kind==="queued"?"Queued":"Generating"})]},ce.id),C.jsxs("div",{className:"inspector-header-actions",children:[$.outputArtifactId&&oo($.type)&&C.jsx("button",{type:"button",className:zt===ce.id?"inspector-source-toggle active":"inspector-source-toggle",title:zt===ce.id?"View cell":"View history","aria-label":zt===ce.id?"View cell":"View history","aria-pressed":zt===ce.id,onClick:()=>{if(zt===ce.id){kt(null);return}Ci(ce.id,$.outputArtifactId)},children:C.jsx(ub,{size:15})}),!an&&C.jsx("button",{type:"button",className:["inspector-source-toggle",oo($.type)?"":"inspector-source-toggle-labeled",Wt===ce.id?"active":""].filter(Boolean).join(" "),title:Wt===ce.id?"View cell":"View source","aria-label":Wt===ce.id?"View cell":"View source","aria-pressed":Wt===ce.id,onClick:()=>{if(Wt===ce.id){Le(null);return}Ii(ce.id)},children:oo($.type)?C.jsx(fb,{size:15}):C.jsxs(C.Fragment,{children:[C.jsx(mb,{size:13,"aria-hidden":"true"}),C.jsx("span",{children:"Source"})]})}),$.type.startsWith("generate_")&&C.jsx("span",{className:"composer-dock-close-divider","aria-hidden":"true"}),C.jsx("div",{ref:ac,className:"inspector-header-action-host"}),C.jsx($i,{label:$.type.startsWith("generate_")?"Close":void 0,shortcut:$.type.startsWith("generate_"),divider:!$.type.startsWith("generate_")})]})]}),hs??(an?C.jsx(vf,{post:an,cells:c?.cells??[],asset:ce.data.asset,bookId:i,call:g.state==="ready"?w:void 0,onRefresh:()=>F(i,c?.id),onSelectCell:Qt,onDeliver:e=>{const t=ls(an.id,e);t.ok||h(t.message,"error")},onReviewX:uu,onDelete:()=>{So([$])}},an.id):C.jsx(rb,{headerActionHost:sc,notebookId:c?.id??"",bookId:i,assetTools:g.state==="ready"?w:void 0,cell:$,cells:c?.cells??[],edges:c?.edges??[],asset:ce.data.asset,cellAssets:nn,versionAssets:cd,status:ce.data.status,error:Ta,queuedCellIds:An,runErrors:so,jobs:ja,onCancelJob:Ha,generationActions:Qe,mentionAssets:se,voiceCatalog:Bn,busy:G||!!ud?.operation,deleting:Sr.has($.id),sourceVisible:Wt===$.id,historyVisible:zt===$.id,history:io&&io.cellId===$.id&&io.assetId===$.outputArtifactId?{revisions:io.revisions,loading:io.loading,error:io.error}:zt===$.id||Wt===$.id&&$.outputArtifactId?{revisions:[],loading:!0,error:null}:void 0,onUpdate:Rd,onSetInput:Pd,onRun:on,onDelete:Md,onOpenFullscreen:(e,t)=>{Vn($,e,void 0,t)},onPreviewPayload:fd,initialGenerationPreview:Ca?.cellId===$.id?Ca:void 0,onSelectSource:Z,onLoadGenerationPayload:md,onInspectGenerationRequest:pd,mediaInsightWork:na,onTranscribeAsset:Sd,onLoadTranscriptJson:kd,onDownloadTranscriptSrt:bd},`${$.id}:${$.prompt??""}`))]}):null),ff=yg({musicSession:!!ve,cellInspector:!!ys}),mf=ys||ve?C.jsx("div",{hidden:!!ve,inert:ve?!0:void 0,children:ys}):null;return C.jsxs("main",{className:`app-shell app-screen-${b} ${Y?"media-fullscreen-open":""}`,onDragEnter:Su,onDragLeave:xu,onDragOver:Eu,onDropCapture:Au,onDrop:_u,onKeyDownCapture:e=>{e.defaultPrevented||(e.ctrlKey||e.metaKey)&&e.shiftKey&&e.key.toLowerCase()==="k"&&!e.nativeEvent.isComposing&&(e.preventDefault(),e.stopPropagation(),Ce())},children:[C.jsxs("header",{className:"topbar",children:[C.jsx("div",{className:"topbar-book-controls",children:C.jsx("div",{className:"brand-project",children:C.jsxs("div",{className:"brand-project-trigger",children:[C.jsxs("button",{type:"button",className:"brand-project-home","data-composer-focus":"return",title:"Open notebook",onClick:()=>Ao("notebook"),children:[C.jsx(pb,{size:18}),C.jsx("span",{children:"/videobook"})]}),C.jsx(yf,{activeBook:co,books:x,disabled:G||g.state!=="ready",error:xc,loading:Sc,open:Cc,onCreate:La,onDelete:Da,onOpenChange:Jt,onRefresh:_d,onRename:Fa,onSelect:Na})]})})}),b==="notebook"&&c&&C.jsx(If,{busy:G||g.state!=="ready",arrangeDisabled:G||g.state!=="ready"||c.cells.length===0,selectedCount:It.length,activeAddress:$?W($.slot):null,onAdd:es,onAddDragEnd:()=>Gt(null),onArrange:$d,onDeleteSelection:Va,onSelectionActions:()=>{Ce(void 0,{cell_id:$?.id,cell_ids:It.map(e=>e.id),artifact_ids:It.flatMap(e=>e.outputArtifactId?[e.outputArtifactId]:[])})},onClearSelection:()=>{Z(null),Le(null),Ut.current?.focus()}}),C.jsxs("div",{className:"topbar-tools",children:[C.jsxs("nav",{className:"header-navigation","aria-label":"Workspace navigation",children:[C.jsx("button",{type:"button",className:z?.cellId===null&&Rr?"active":"",title:"Library","aria-label":"Open Library","aria-expanded":z?.cellId===null&&Rr,disabled:G||g.state!=="ready"||!c,onClick:()=>os(),children:C.jsx($l,{size:17})}),nw.map(e=>{const t=e.icon;return C.jsx("button",{type:"button",className:b===e.id?"active":"",title:e.label,"aria-label":`Open ${e.label}`,"aria-current":b===e.id?"page":void 0,onClick:()=>Ao(e.id),children:C.jsx(t,{size:17})},e.id)})]}),C.jsx(Cf,{bookName:co?.name??"",enabled:!!i,snapshot:Br.snapshot,stale:Br.stale,onRetry:Br.retry},i)]})]}),!_t&&C.jsx("div",{className:"offline-banner",role:"status",children:"Offline · local import, search, editing, playback, history, and export remain available"}),C.jsxs(C.Fragment,{children:[b==="notebook"&&C.jsx(C.Fragment,{children:C.jsx("section",{className:"canvas",style:Ic,children:c?C.jsx("div",{className:"notebook-horizontal-scroll","data-composer-focus":"return",ref:Ut,tabIndex:0,"aria-label":"Notebook canvas",onKeyDown:Td,children:C.jsx("div",{className:"notebook-flow-frame",style:Bc,children:C.jsx(Sf.Provider,{value:ws,children:C.jsx(xf.Provider,{value:Tu,children:C.jsx(Ef.Provider,{value:on,children:C.jsx(Af.Provider,{value:of,children:C.jsx(_f.Provider,{value:Me,children:C.jsx(Rf.Provider,{value:lc,children:C.jsx(Pf.Provider,{value:Vc,children:C.jsx(Mf.Provider,{value:Ia,children:C.jsx(Tf.Provider,{value:re,children:C.jsx(jf.Provider,{value:Lc,children:C.jsxs(gf,{className:"notebook-flow",nodes:Uc,edges:Wc,nodeTypes:fw,edgeTypes:mw,viewport:Hc,onInit:e=>{Oo.current=e},onNodesChange:e=>{const t=e.filter(o=>o.type==="select");if(t.length>0){const o=new Set(lt.current);for(const l of t)l.selected?o.add(l.id):o.delete(l.id);bo(o);const n=[...o].at(-1)??null,r=Me&&o.has(Me)?Me:n;qo(r),Yo(r);const s=n?c?.cells.find(l=>l.id===n):void 0,a=n?ze.find(l=>l.id===n):void 0;s?Ae(s.slot):a&&Ae(a.data.slot)}ht(o=>{let n=ji(e,o);for(const r of e)r.type!=="position"||!r.dragging||!r.position||(n=Lp(n,r.id,Ms(r.position)));return n})},onEdgesChange:e=>{$n(o=>bf(e,o));const t=e.filter(o=>o.type==="remove").map(o=>o.id);t.length>0&&Ld(t)},onNodeClick:(e,t)=>{const o=lt.current,n=o.has(t.id)?t.id:[...o].at(-1)??null;qo(n),Yo(n),n===t.id&&Ae(t.data.slot),Le(null),t.type!=="timeline"&&no("selection")&&me(!0),t.type!=="timeline"&&o.size===1&&n===t.id&&!e.shiftKey&&!e.metaKey&&!e.ctrlKey&&(ao(t.id),z?.cellId!==t.id&&xo(t.id))},onPaneClick:()=>{wo(),Z(null),Le(null)},onPaneContextMenu:e=>{if(Qn.length===0)return;const t=hi(e.clientX,e.clientY);t&&(e.preventDefault(),Oc(t,{x:e.clientX,y:e.clientY},document.activeElement instanceof HTMLElement?document.activeElement:null))},onNodeDrag:(e,t)=>{wo(),Gt(Ms(t.position))},onNodeDragStop:(e,t,o)=>{const n=ji(o.map(({id:a})=>({id:a,type:"position",dragging:!1})),ze),r=qp(n,t.id,o.map(a=>a.id),Ms(t.position)),s=Np(ze,r);if(ht(r),Gt(null),s.length>0){const a=s.find(l=>l.id===t.id)??s[0];a&&Ae(a.data.slot),jd(s)}},isValidConnection:e=>c?ll(c.edges,e,c.cells):!1,onConnect:e=>{Nd(e)},onDrop:Mu,onDragLeave:Ru,onDragOver:Pu,minZoom:je,maxZoom:je,defaultEdgeOptions:gw,elementsSelectable:!0,multiSelectionKeyCode:kw,panOnDrag:bw,panOnScroll:!1,selectionKeyCode:null,selectionMode:kf.Partial,selectionOnDrag:!0,selectNodesOnDrag:!1,zoomOnScroll:!1,zoomOnPinch:!1,zoomActivationKeyCode:null,zoomOnDoubleClick:!1,preventScrolling:!1,deleteKeyCode:null,proOptions:pw,children:[C.jsx(Lf,{sections:zc,metrics:Tt,occupiedSlots:vt,previewSlot:Lo,mediaDropActive:ia&&!G,mediaDropSlot:wc,reviewRoles:Gr}),ze.length===0&&C.jsx(Ff,{busy:G||g.state!=="ready",compact:Ki(je)>1.8,dimmed:ia||Lo!==null,onUpload:(e,t)=>{ts(e,t)},onPick:(e,t)=>{es(e,$p(t))},onDownload:ru,onBrowseLibrary:os})]})})})})})})})})})})})})}):C.jsxs("div",{className:"canvas-empty-state",children:[C.jsx("strong",{children:"No notebook available"}),C.jsx("button",{type:"button",onClick:()=>{Ad(i)},children:"Reload book"})]})})}),b==="jobs"&&C.jsx(nb,{bookName:co?.name??null,jobs:Ve,plans:Ur,assets:B,cells:c?.cells??ow,now:tc,busy:G,onRefresh:()=>i&&void F(i,c?.id),onCancelJob:e=>{Ha(e)},onRetryJob:e=>{zd(e)},onContinuePlan:e=>{const t=Ur.find(o=>o.planId===e);t&&Hd(t)},onRevisePlan:(e,t)=>{const o=Ur.find(n=>n.planId===e);o&&Bd(o,t)}}),b==="settings"&&C.jsx(Df,{call:g.state==="ready"?w:void 0,providers:cc,loading:fc,error:mc,refreshed:pc,storage:uc,bookId:i,bookName:co?.name??null,connection:$o,busy:G||g.state!=="ready",onRefresh:ln,onSave:Kd,onConnect:()=>{ns()}})]}),Ye&&ee&&C.jsx(qi,{actions:Be,address:W(ee.slot),cellType:Ps(ee.type),deleteDisabled:G||Sr.has(ee.id),menuId:Of(ee.id),position:Ye.position,returnFocus:Ye.returnFocus,onAction:Yu,onClose:wo,onDelete:Zu}),Ye&&_o&&Qn.length>0&&C.jsx(qi,{actions:Qn,address:W(_o),cellType:"EMPTY",menuId:uw(_o),menuLabel:`Slot actions for ${W(_o)}`,position:Ye.position,returnFocus:Ye.returnFocus,onAction:Ku,onClose:wo}),ve&&J&&C.jsx(m.Suspense,{fallback:C.jsx("div",{role:"status",children:"Loading music-video editor…"}),children:C.jsx(Ol,{assembly:et,rhythm:wt,onFrameUpdate:et.seek,onExport:()=>{ni(),ws.onExport()},sequence:J,assets:B,audioArtifactId:ve.audioArtifactId,setup:ve.setup,returnFocus:ve.returnFocus,onApplySetup:Qa,onClose:()=>{wt.stop(),ni()},onCommit:Ya,onPlanDraft:Za,onApplyDraft:ei,onCreateTrack:oi,onRefreshAssets:async()=>{if(!i)throw new Error("Load or create a book first.");await F(i,c?.id)},onRestore:ti,onReviewSetup:e=>Xa(ve.key,ve.audioArtifactId,e??J)},ve.key)}),it&&C.jsx(m.Suspense,{fallback:C.jsx("div",{role:"status",children:"Loading alive captions…"}),children:C.jsx(zb,{asset:it.asset,state:it.state,returnFocus:it.returnFocus,onClose:ou,onSave:e=>ai(it.asset.artifactId,e),onRender:(e,t)=>nu(it.asset.artifactId,e,t),onReanalyze:()=>si(it.key,it.asset.artifactId,!0)},it.key)}),Qo&&Xo&&jn&&J&&C.jsx(m.Suspense,{fallback:C.jsx("div",{role:"status",children:"Opening timeline preview…"}),children:C.jsx(Ol,{sequence:J,assets:B,assembly:et,rhythm:wt,setup:{status:"timeline"},address:W(jn.slot),initialFrame:Xo.initialFrame,returnFocus:Xo.returnFocus,onFrameUpdate:et.seek,onExport:()=>{Ri(),ws.onExport()},onClose:Ri,onApplySetup:Qa,onCommit:Ya,onPlanDraft:Za,onApplyDraft:ei,onCreateTrack:oi,onRefreshAssets:async()=>{await F(i,c?.id)},onRestore:ti,onReviewSetup:async()=>{await wt.load()}},`${i}:${jn.id}`)}),Y&&C.jsx(sb,{asset:Y.asset,address:Y.address,initialMode:Y.mode,initialInstruction:Y.initialInstruction,onInstructionChange:e=>{sa.current.set(Y.bookId,e),Ot(`videobook.image-edit-instruction:${Y.bookId}`,e)},composerPortalRef:Ar,actionsOpen:!!Ro,subjectMap:Y.subjectMap,subjectMapLoading:Y.subjectMapLoading,returnFocus:Y.returnFocus,analysisUnavailableReason:Y.asset.type==="image"&&!Y.asset.objectHash?"This version is missing its immutable object hash. Refresh the book data and reopen it.":null,onAnalyzeSubjects:e=>Id(Y,e),onCaptureFrame:Y.asset.type==="video"||Y.asset.type==="final"?e=>yd(Y,e):void 0,onEditingChange:_r,replacementCandidates:nf,imageEditModels:Jo.models,imageEditModelsLoading:Jo.loading,defaultImageEditModelId:Jo.defaultModelId,onEstimateImageEditCost:Fc,onEditSubjects:e=>Gn(Y,e),onSubmitEditInstruction:(e,t)=>Cu(Y,e,t),onClose:Kt},Y.key),C.jsx("input",{ref:Bs,type:"file",multiple:!0,hidden:!0,"aria-label":"Import files from actions",onChange:Ud}),Ne&&C.jsx(Vf,{media:Ne.media,sequence:Ne.media?void 0:J??void 0,assets:B.flatMap(e=>e.mediaUrl?[{artifactId:e.artifactId,mediaUrl:e.mediaUrl}]:[]),opener:Ne.opener,initialFrame:Ne.initialFrame,composerPortalRef:rc,actionsOpen:!!(Ro||Ei),onClose:()=>{jo(null),gt(null),Vt(null)},onActions:()=>{Ce(void 0,Ne.media?{asset_id:Ne.media.assetId}:void 0)}}),qe?.actionId&&C.jsx(Gf,{actions:Et,context:{...fn,entities:qe.resources?.entities,choices:{...fn.choices,...qe.resources?.choices}},initialActionId:qe.actionId,initialValues:qe.values,initialResult:qe.result,returnFocus:qe.opener,loading:br.loading,error:br.error,onClose:()=>{at.current+=1,Xe(null)},onBack:()=>{Ce(void 0,qe.values,qe.query,qe.opener)},onOpenAction:(e,t)=>{Ce(e,{...qe.values,...t})},onExecute:vu,onReview:yu},qe.key),C.jsx(Uf,{chatTurns:fa,goalEvents:qc,previewTurnId:Ac,connected:g.state==="ready"&&_t,onBeginTurn:wi,onCommandRowHeightChange:vc,onHeightChange:yc,hidden:!ks,dockOpen:Rr,onDockOpenChange:me,contextualContent:mf,contextualHasHeader:ff,goalStatus:fo?C.jsx(cb,{goal:fo,disabled:g.state!=="ready",onOpen:()=>Zr(fo.cellId)}):null,commands:cf,references:Vr,actions:Et,actionContext:fn,actionDiscovery:rf,actionStatus:br,actionsDisabled:G||g.state!=="ready",onOpenActions:()=>{Ce()},onCloseActionSearch:e=>{gt(null),!e&&Ai&&qa()},onDismissComposer:Ai?qa:void 0,bookId:i,callTool:w,chatModels:vr.models,disabled:G||aa||!i||g.state!=="ready",modelSelectionDisabled:!i||g.state!=="ready",connectionLabel:aa?"Removing selected subjects…":g.state==="ready"?"Load a book to begin":"Connecting to MCP…",mcpCalls:Rc,mcpFlash:Pc,onToggleMcpCall:Dc,selectedModel:Hs,inputSession:Yn,portalTarget:Ne&&(Ro||Ei)?nc:Y&&Ro?bc:null,pendingInput:he?"/apply":E?.kind==="generation"||E?.kind==="transcribe"?"/apply ":ue||E?"/apply":void 0,replacePendingInput:E?.kind==="transcribe",notice:Bt?{message:Bt.text,tone:Bt.tone}:null,outcomeSlot:_i?"sheet":"composer",onEnsureCatalog:xd,onDismissNotice:()=>Do(null),onDismissPanel:he||ue||E?Fe:void 0,onExecute:ms,voiceCatalog:Bn,voice:Yt,onStartVoice:()=>{Z(null),wo(),Vt(null),Le(null),kt(null)},onModelChange:Ed,onSuccessfulExecute:lf,children:_i})]})}const hw=await zk().catch(()=>null);pf.createRoot(document.getElementById("root")).render(C.jsx(ww,{initialWorkspace:hw}));
|
|
37
|
+
Continue and remember this choice on this device?`))return{ok:!1,message:"Cloud generation cancelled before sending data",nextInput:r,selectInput:!1};window.localStorage.setItem(u,"accepted")}const d=n.draft.cell.id,p=W(n.draft.cell.slot);let v=!1,S=!1;T(!0),ne(d,null),oe(d,!0),Ae(n.draft.cell.slot),Z(d,o,a),wu(n.draft,s);try{await vl({bookId:i,callTool:(B,te)=>w(B,te,{chat:o}),document:s,draft:n.draft,...s.revision?{expectedRevision:s.revision}:{}}),v=!0;const A=await bo(d,"chat",o),y=await w("run_notebook_cell",{book_id:i,notebook_id:s.id,cell_id:d,plan:A,actor:"videobook-user"},{chat:o});S=!0;const R=D(y);ae(o);const q=_(R?.run_id),V=_(R?.job_id),X=_(R?.output_cell_id);if(L(o,!1,()=>O(null)),$r.current||ko(),oe(d,!1),!q||!V)return await F(i,s.id,void 0,o).catch(()=>{}),{ok:!0,message:`${p} was accepted; follow its status in Jobs`};M(o,()=>h(`${p} queued`));const P=X??d;let N=Se(n.draft.cell.slot);if(X){const B=await $e(i,s.id,o).catch(()=>null);M(o,()=>{en([X]),go([X],{scroll:"center"})}),ne(X,null),oe(X,!0);const te=B?.cells.find(de=>de.id===X);te&&(N=Se(te.slot))}else go([d],{scroll:"center"});return tn({bookId:i,notebookId:s.id,cellId:P,address:N,runId:q,jobOperationId:V},o),await F(i,s.id,void 0,o).catch(()=>{}),{ok:!0,message:`${p} queued`}}catch(A){const y=A instanceof Error?A.message:String(A),R=y.startsWith("Stale notebook revision:");return v&&!S&&await w("delete_notebook_cell",{book_id:i,notebook_id:s.id,cell_id:d},{chat:o}).catch(()=>{}),S||(ht(q=>q.filter(V=>V.id!==d)),oe(d,!1)),ne(d,y),await F(i,s.id,void 0,o).catch(()=>{}),R?(L(o,!1,()=>O(null)),M(o,()=>h("Notebook changed since this preview; prepare the action again.","error")),{ok:!1,message:"Notebook changed since this preview; prepare the action again."}):(M(o,()=>h(y,"error")),{ok:!1,message:y,nextInput:r,selectInput:!1})}finally{T(!1)}},pi=async(e,t,o)=>{const n=t??e.languageCode,r=rl({assetId:e.assetId,languageCode:n}),s=t?`/apply ${t}`:"/apply ";if(r.blocking||!e.assetId||!i)return{ok:!1,message:r.blocking??"Choose a video or audio clip.",nextInput:s,selectInput:!1};const a=e.assetId,l=na[a]??Qi;if(Gk(l))return{ok:!1,message:"Transcription is already running for this clip.",nextInput:s,selectInput:!1};t!==null&&t!==e.languageCode&&M(o,()=>O(y=>y?.kind==="transcribe"?{...y,languageCode:n}:y));const u=c?.id,d=zl(re.get(a),"transcript"),p=Date.now();rn(a,{...bn("transcript",!0),error:null});try{await w("transcribe",cl({bookId:i,assetId:a,languageCode:n,diarize:e.diarize,tagAudioEvents:e.tagAudioEvents}),{chat:o})}catch(y){const R=y instanceof Error?y.message:String(y);return rn(a,{...bn("transcript",!1),error:R}),{ok:!1,message:R,nextInput:s,selectInput:!1}}L(o,!1,()=>O(null));const v=se.find(y=>y.artifactId===a)?.cellAddress,A=`Transcription queued for ${v?`@${v}`:re.get(a)?.label??a}`;return M(o,()=>h(A)),u?kd({bookId:i,notebookId:u,artifactId:a,insight:"transcript",since:p,hadInsight:d}).then(y=>{rn(a,{...bn("transcript",!1),error:y.kind==="failed"?y.message:null})}).catch(y=>{rn(a,{...bn("transcript",!1),error:y instanceof Error?y.message:String(y)})}):rn(a,{...bn("transcript",!1),error:null}),{ok:!0,message:A,nextInput:""}},vu=async(e=null,t)=>{if(!E||!i)return{ok:!1,message:"There is no pending chat action."};if(E.kind==="cold-open"){const o=E.review,n=()=>Q.current.bookId===o.bookId&&Q.current.notebookId===o.notebookId&&(t?.isCurrent()??!0),r=(a,l,u)=>w(a,l,{...u,chat:t});if(!o.suggestion){const a=await Pk(r,o,n);return L(t,!0,()=>O({kind:"cold-open",review:a})),pt("Adjust the highlight, then create the copy")}const s=await Mk(r,o,n);return await F(o.bookId,o.notebookId,n,t),n()?(L(t,!1,()=>O(null)),Z(s.cellId),ae(t),{ok:!0,message:`Cold-open copy created as ${s.address}`}):{ok:!0,message:`Cold-open copy created as ${s.address}`}}if(E.kind==="post-delivery"){const o=E.review,n=dn.find(d=>d.id===o.postId)??null,r=al(n,o);if(!n||r.blocking)return{ok:!1,message:r.blocking??"This Post is no longer on the canvas."};const s=()=>Q.current.bookId===o.bookId&&Q.current.notebookId===o.notebookId&&(t?.isCurrent()??!0),a=Tk(n,o);a&&await w("update_post",a,{chat:t});const l=await w(jk(o.destination),$k(n,o),{chat:t});await F(o.bookId,o.notebookId,s,t);const u=qk(l,o.destination);return s()&&L(t,!0,()=>O({kind:"post-delivery",review:{...o,icloudFolder:l.runtime.icloud?.folder??o.icloudFolder,dropboxFolder:l.runtime.dropbox?.folder??o.dropboxFolder,receipt:u,sync:null}})),{ok:!0,message:u}}if(E.kind==="transcribe"){if(e){const o=Nk(e);return o.ok?await pi(E,o.languageCode,t):{ok:!1,message:o.message,nextInput:`/apply ${e}`,selectInput:!1}}return await pi(E,null,t)}if(E.kind==="generation")return await hu(E,e,t);if(E.kind==="routed"&&(E.plan.tool==="post"||E.plan.routedTool==="post")){const o=Oi(Fi(E.plan.params),void 0,Sn),n=E.xPostReview?.options.enabled&&to(E.xPostReview).length===0?Di:null;if(o||n)return{ok:!1,message:o??n??"The post is not ready.",nextInput:"/apply",selectInput:!1}}if(E.kind==="frame"||E.kind==="split"||E.kind==="notebook"){const o=ge(await w("get_notebook",{book_id:i,notebook_id:E.notebookId},{chat:t}));if(!o)return{ok:!1,message:"The server returned an invalid notebook"};const n=E.kind==="notebook"?E.plan.expectations:E.expectations;if(Pl(o,n))return L(t,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."};if(E.kind==="frame"){const s=await ii(E.command,o,void 0,t);if(s.ok)L(t,!1,()=>O(null));else if(s.message.startsWith("Stale notebook revision:"))return L(t,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."};return s}if(E.kind==="split"){const s=await iu(E.command,o,t);if(s.ok)L(t,!1,()=>O(null));else if(s.message.startsWith("Stale notebook revision:"))return L(t,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."};return s}const r=E.plan.action;if(r.kind==="run"){const s=Po(o,r.source),a=await on(s.id,o,t);return a?.ok?(L(t,!1,()=>O(null)),{ok:!0,message:`Run requested for ${W(s.slot)}`}):a?.message.startsWith("Stale notebook revision:")?(L(t,!1,()=>O(null)),{ok:!1,message:"Notebook changed since this preview; prepare the action again."}):a??{ok:!1,message:`Could not run ${W(s.slot)}`}}T(!0);try{const s=o.revision?{expected_revision:o.revision}:{};if(r.kind==="create"){const a=r.destination,l=D(await w("create_notebook_cell",{book_id:i,notebook_id:o.id,...s,cell:{type:r.cellType,slot:a,...r.cellType==="prompt"||r.cellType==="analyze"||no(r.cellType)?{prompt:""}:{}}},{chat:t})),u=_(l?.id);u&&Z(u,t)}else if(r.kind==="move"){const a=Po(o,r.source),l=Po(o,r.destination);await w("move_notebook_cells",{book_id:i,notebook_id:o.id,...s,slots:[{id:a.id,row:r.destination.row,column:r.destination.column},...l?[{id:l.id,row:r.source.row,column:r.source.column}]:[]]},{chat:t})}else if(r.kind==="delete"){const a=Po(o,r.source);await w("delete_notebook_cell",{book_id:i,notebook_id:o.id,cell_id:a.id,...s},{chat:t})}else if(r.kind==="connect"){const a=Po(o,r.source),l=Po(o,r.target),u=r.targetInput??pl(o,{source:a.id,target:l.id,targetHandle:null});await w("set_notebook_cell_input",{book_id:i,notebook_id:o.id,source_cell_id:a.id,target_cell_id:l.id,target_input:u,...s},{chat:t})}else throw new Error("Unsupported notebook action");return L(t,!1,()=>O(null)),await F(i,o.id,void 0,t),r.kind==="create"&&ae(t),M(t,()=>h(E.plan.summary)),{ok:!0,message:E.plan.summary}}catch(s){const a=s instanceof Error?s.message:String(s);return a.startsWith("Stale notebook revision:")?(L(t,!1,()=>O(null)),M(t,()=>h("Notebook changed since this preview; prepare the action again.","error")),{ok:!1,message:"Notebook changed since this preview; prepare the action again."}):(M(t,()=>h(a,"error")),{ok:!1,message:a,nextInput:"/apply",selectInput:!0})}finally{T(!1)}}return E.kind==="chain-step"?await du(E,t):await mi(E.plan,void 0,t)},gi=async(e,t,o,n,r)=>{if(e==="download_video"&&c)return await Bn(t,_(o.url)??"",void 0,r);const s=c?Il(e,t,c.cells,Ge):[];if(c&&s.length>0){const a=[];let l=null;for(const d of s){const p=D(await w("create_notebook_cell",{book_id:i,notebook_id:c.id,cell:d},{chat:r})),v=_(p?.id);if(!v)throw new Error("The server did not return the new notebook cell");l??=v,a.push(W(d.slot))}Q.current.bookId===i&&(Z(l,r),await F(i,c.id,void 0,r));const u=`Created ${a.join(" and ")}`;return ae(r),M(r,()=>h(u)),{ok:!0,message:u}}if(Q.current.bookId===i){const a=await F(i,c?.id,void 0,r);ir(c,a)&&ae(r)}if(e==="rename_asset"){const a=D(t),l=_(a?.label);return{ok:!0,message:l?`Renamed asset to ${l}`:"Asset renamed"}}return{ok:!0,message:kn(t,`${n} complete`)}},ki=async(e,t,o,n)=>{const r=i,s=D(await w("asset_manifest",{book_id:r,asset_id:e.artifactId},{chat:n}));if(Q.current.bookId!==r)return;const a=(Array.isArray(s?.files)?s.files:[]).flatMap(d=>{const p=_(D(d)?.name);return p?[{name:p,url:`/files/${encodeURIComponent(r)}/${encodeURIComponent(e.artifactId)}/${p.split("/").map(encodeURIComponent).join("/")}`}]:[]}),l=t==="original"?a.find(d=>d.name.startsWith("original.")):t?a.find(d=>d.name.startsWith(`${t}.`)):o?a[o-1]:void 0;if((t||o)&&!l)throw new Error(t?`No ${t} file exists yet. Use render video to create it.`:"That file position does not exist.");const u=document.activeElement instanceof HTMLElement?document.activeElement:null;M(n,()=>jo({media:{label:e.label,assetId:e.artifactId,type:e.type,url:e.mediaUrl,thumbnailUrl:e.thumbnailUrl,files:a,initialFile:l?.name,opener:u},opener:u,turnId:n?.id}))},bi=async(e,t,o)=>{if(e.handler.kind!=="ui")return null;const n=e.handler.action,r=nk[n];if(r.kind==="existing")return null;if(r.kind==="library")return os(),{ok:!0,message:"Library opened"};if(r.kind==="screen")return Qt(r.screen),{ok:!0,message:`${r.screen==="jobs"?"Jobs":"Settings"} opened`};const s=_(t.asset_id??t.asset_ref??t.artifact_id)??Ne?.media?.assetId??Y?.asset.artifactId??$?.outputArtifactId,a=H.find(l=>l.artifactId===s)??H.find(l=>se.some(u=>u.artifactId===l.artifactId&&u.cellAddress.toLowerCase()===s?.replace(/^@/u,"").toLowerCase()));if(r.kind==="search")return await Ce(void 0,void 0,r.query,void 0,o),{ok:!0,message:"Actions opened"};if(r.kind==="form"){const l=e.command==="/storage"?"storage_status":r.tool,u=J?J.frameRate.numerator/J.frameRate.denominator:30,d=rk(n,t,u);if(a&&(d.asset_id=a.artifactId),n.startsWith("timeline_audio_")&&n!=="timeline_audio_add"&&t.audio_ref){const p=sk(String(t.audio_ref),J,H,se);if(!p.ok)return p;d.audio_id=p.clipId}return n==="viewer_focus_file"&&a?await ki(a,void 0,ak(t.position),o):await Ce(`tool.${l}`,d,void 0,void 0,o),{ok:!0,message:`${e.title} options opened`}}if(r.action==="upload")return Hs.current?.click(),{ok:!0,message:"Choose files to import"};if(r.action==="notebook"){const l=_(t.name)?.trim();if(l){const d=Zi(await w("list_notebooks",{book_id:i},{chat:o})).find(p=>p.name===l||p.id===l);if(!d)return await Ce("tool.create_notebook",{name:l},void 0,void 0,o),{ok:!0,message:"Create notebook options opened"};await F(i,d.id,void 0,o)}else if(!c)return await Ce("tool.create_notebook",{name:"scratch"},void 0,void 0,o),{ok:!0,message:"Create notebook options opened"};return Qt("notebook"),{ok:!0,message:"Notebook opened"}}if(r.action==="save"){if(!c)throw new Error("Open a notebook first.");return await $e(i,c.id,o),{ok:!0,message:"Notebook changes are saved automatically. Saved state verified."}}if(r.action==="collapse"||r.action==="expand"){const l=r.action==="expand",u=ik(_(t.side));return u!=="left"&&(!l||ro("expand"))&&me(l),u!=="right"&&(l?await So():Pr(!1)),{ok:!0,message:l?"Workspace panels opened":"Workspace panels closed"}}if(r.action==="close")return Kt(),M(o,()=>jo(null)),{ok:!0,message:"Viewer closed"};if(r.action==="play"){const l=lk(_(t.slot),J);return l.ok?(M(o,()=>jo({initialFrame:l.initialFrame,turnId:o?.id,opener:document.activeElement instanceof HTMLElement?document.activeElement:null})),{ok:!0,message:"Sequence preview opened"}):{ok:!1,message:l.message}}if(!a)return await Ce(e.id,t,void 0,void 0,o),{ok:!0,message:"Choose media for this action"};if(r.action==="copy")return await navigator.clipboard.writeText(a.label),{ok:!0,message:"Media label copied"};if(r.action==="history"){const l=c?.cells.find(u=>u.outputArtifactId===a.artifactId);return l?Ci(l.id,a.artifactId):await Ce("tool.asset_history",{asset_id:a.artifactId},void 0,void 0,o),{ok:!0,message:"Media history opened"}}if(r.action==="skeleton"){if(a.type!=="image")throw new Error("Choose an image for a pose guide.");return await Ce("tool.generate_image",{model:"kie:qwen3/image-to-image",refs:{image:[a.artifactId]},prompt:"Create a pose skeleton guide from this reference image. Preserve the visible body poses, joint positions and framing. Show only clearly connected colored skeleton joints and limbs on a black background, without clothing, faces, scenery or text."},void 0,void 0,o),{ok:!0,message:"AI pose guide options opened. Review the provider and cost before generating."}}return await ki(a,r.action==="open"?void 0:r.action,void 0,o),{ok:!0,message:"Media preview opened"}},fs=async(e,t,o)=>{try{const n=e.trim().toLowerCase(),r=qs(e);if(r)return r.promptOverride&&(he||E?.kind!=="generation"&&E?.kind!=="transcribe")?{ok:!1,message:"A quick prompt can only revise a pending generation.",nextInput:e,selectInput:!1}:he?await Gd(o):E?await vu(r.promptOverride,o):ue?await Qd(o):{ok:!1,message:"There is no pending action to apply."};if(n==="/cancel")return!he&&!E&&!ue?{ok:!1,message:"There is no pending action to cancel."}:(L(o,!1,()=>Te(null)),L(o,!1,()=>O(null)),L(o,!1,()=>le(null)),{ok:!0,message:"Pending action cancelled"});if(he&&L(o,!1,()=>Te(null)),!i&&!e.startsWith("/"))return{ok:!1,message:"Load or create a book first."};if(!e.startsWith("/")){const P=await w("chat",{book_id:i,...c?{notebook_id:c.id}:{},prompt:e,model:Bs},{chat:o});return D(P)?.kind==="chat-action-plan"?await Kn(Ts(P),e,void 0,o):(L(o,!1,()=>O(null)),L(o,!1,()=>le(null)),hl(P)?await Bn(P,Kl(e),void 0,o):(await F(i,c?.id,void 0,o),{ok:!0,message:kn(P,"Command complete")}))}const[s,...a]=e.trim().split(/\s+/),l=s.toLowerCase(),u=a.join(" ");if(l==="/goal")return await hd(u,o);if(l.toLowerCase()==="/actions")return await Ce(void 0,void 0,u,void 0,o),{ok:!0,message:"Actions opened"};const d=l.toLowerCase()==="/duplicate"?[ar(a[0]??"",Uo),...a.slice(1)].filter(Boolean).join(" "):ar(u,Uo);if(l==="/transcribe"){const P=d.split(/\s+/).find(N=>N.length>0);return sn({assetRef:P,chat:o})}const p=Et.length?Et:As(await w("list_workspace_actions",{detail:"full"},{chat:o})).actions;Et.length||kr(p);const v=Dl(or(p,In),l,d),S=p.find(P=>[P.command,...P.aliases].includes(l));if(v?.workspaceActionId||S&&!u&&(S.inputSchema.required??[]).some(P=>!["book_id","notebook_id","sequence_id"].includes(P))){const P=v?mt(d,v.params):{};return await Ce(S?.id??v?.workspaceActionId,P,void 0,void 0,o),{ok:!0,message:"Action options opened"}}if(l==="/extract-audio")return!c||a.length!==1?{ok:!1,message:"Usage: /extract-audio @video"}:await li({sourceReference:pr(a[0])},void 0,o);if(l==="/split"){const P=Wg(e);return P?await cn(P,void 0,o):{ok:!1,message:"Usage: /split @video [at 5s, 12.5s] | keep 0.03-0.11 | remove 0.03-0.11"}}if((l==="/split-chunks"||l==="/even-split")&&new RegExp(`^@${Yl}$`,"iu").test(a[0]??"")){const[P,...N]=a,B=(N.length>0?N:["7"]).map(te=>Number(te.replace(/\s*s(?:ec(?:onds?)?)?$/iu,"")));return B.some(te=>!Number.isFinite(te)||te<=0)?{ok:!1,message:"Split durations must be positive seconds."}:await cn({sourceReference:pr(P),cutPointsSeconds:bl(B)},void 0,o)}if(l==="/rough-cut")return await Zd("slash",o);if(l==="/sound-effects")return await eu("slash",o);if(l==="/generate-cell"){if(!c||a.length!==1)return{ok:!1,message:"Usage: /generate-cell @cell-id"};const P=pr(a[0]),N=c.cells.find(B=>B.id.toLowerCase()===P||W(B.slot).slice(1).toLowerCase()===P);return!N||!Hi(N)?{ok:!1,message:"Choose a configured generation cell"}:await Kr(N.id,"slash",o)}if(l==="/arrange-videos-column"||l==="/arrange-videos-row"){const P=$?.slot??Ge;return P?await Nd(l==="/arrange-videos-column"?"column":"row",P,o):{ok:!1,message:"Select a cell to anchor the arrangement"}}if(l==="/group-images"){const P=$?.slot??Ge;return P?await Ga(P,o):{ok:!1,message:"Select a cell to anchor the grouping"}}if(l==="/track-add"){const P=zg(a);return P.ok?await tu(P.kind,P.name,o):P}if(l==="/track-remove"){const P=lw(J,a[0]);return!P||a.length!==1?{ok:!1,message:"Usage: /track-remove @track-id"}:await ou(P.trackId,o)}if(l==="/export-sequence"||l==="/export"&&a.some(P=>P==="@sequence-main"||P.startsWith("--")||P===`@${J?.sequenceId}`)){if(!J)return{ok:!1,message:"Load the primary sequence first."};const P=Hg(a,J.sequenceId);if(!P.ok)return P;const{orientation:N,captions:B}=P,te=Ke(await w("get_primary_sequence",{book_id:i},{chat:o}));if(!te)return{ok:!1,message:"Load the primary sequence first."};Ee(te);const de=await w("plan_sequence_export",{book_id:i,source_surface:"slash",actor:"videobook-user",sequence_revision:te.revision,orientation:N,captions:B},{chat:o}),pe=D(de);if(pe?.kind==="invalid-export"){const Be=D(pe.validation);return{ok:!1,message:(Array.isArray(Be?.errors)?Be.errors.map(Oe=>_(D(Oe)?.message)).filter(Boolean):[]).join(" · ")||"Export validation failed"}}return await Xt(ft(de),o)}const A=Bg(l,a,{sequence:J,assets:H,mentionAssets:se});if(A.handled)return A.ok?await Ja(A.request,"slash",o):A;const y=Dl(In,l,d);if(!y)return{ok:!1,message:`Unknown command: ${l}`};if(S?.handler.kind==="ui"){const P=y.command==="/post"?Vb(d):mt(d,y.params),N=await bi(S,P,o);if(N)return N}if(y.uiAction==="switch_book"){const P=y.command.slice(1),N=x.find(te=>te.name.toLowerCase()===P.toLowerCase());if(!N)return{ok:!1,message:`Book not found: ${P}`};const B=await Na(N.bookId);return B.ok?{ok:!0,message:`Opened ${N.name}`}:{ok:!1,message:B.error}}if(y.uiAction==="open_projects"){const P=await So();return P.ok?{ok:!0,message:"Project selector opened"}:{ok:!1,message:P.error}}if(y.uiAction==="open_notebook")return tt("notebook"),{ok:!0,message:"Notebook opened"};if(y.uiAction==="x_connect")return tt("settings"),ln(),await ns();if(y.uiAction==="open_provider_keys")return tt("settings"),await ln(),{ok:!0,message:"Settings opened"};if(y.uiAction==="open_music_video"){if(!J)return{ok:!1,message:"Load the primary sequence first."};const P=mt(d,y.params),N=_(P.audio_ref),B=Kg(N,H);if(!B.ok)return B;const te=B.asset,de=xt(),pe=document.activeElement instanceof HTMLElement&&document.activeElement!==document.body?document.activeElement:document.querySelector('[aria-label="Videobook command input"]');return M(o,()=>No(null)),Tn(null),wt.load(),Ue({key:de,audioArtifactId:te.artifactId,returnFocus:pe,setup:{status:"loading"}}),ro("action")&&me(!0),Xa(de,te.artifactId,J,o).catch(()=>{}),{ok:!0,message:`Music-video editor opened for ${te.label}`}}if(y.uiAction==="open_alive_captions"){const P=mt(d,y.params),N=Jg(_(P.asset_ref),H);if(!N.ok)return N;const B=N.asset,te=xt(),de=document.activeElement instanceof HTMLElement&&document.activeElement!==document.body?document.activeElement:document.querySelector('[aria-label="Videobook command input"]');return M(o,()=>No(null)),Tn(null),Ue(null),Er({key:te,asset:{artifactId:B.artifactId,label:B.label,mediaUrl:B.mediaUrl,width:B.width,height:B.height,fps:B.fps},returnFocus:de,state:{status:"loading"}}),si(te,B.artifactId,!1,o),{ok:!0,message:`Alive captions opened for ${B.label}`}}if(y.uiAction==="speak_preview"){const P=mt(d,y.params),N=Xg({command:y.command,text:_(P.text)??"",voiceId:t?.speakVoiceId,hasNotebook:!!c});return N.kind==="prefill"?{ok:!0,message:N.message,nextInput:N.nextInput,selectInput:!1}:N.kind==="error"?{ok:!1,message:N.message}:await Vd(N.text,N.voiceId,o)}if(y.uiAction==="open_cold_open"){const P=mt(d,y.params);return ss(_(P.asset_ref)??void 0,o)}if(y.uiAction==="open_post_dropbox"||y.uiAction==="open_post_icloud")return cs(u||void 0,y.uiAction==="open_post_dropbox"?"dropbox":"icloud",o);if(y.uiAction==="open_watermark"){const P=mt(d,y.params),N=kl(_(P.asset_ref)??void 0,$,H,new Map(se.map(B=>[B.artifactId,B.cellAddress])));return N.ok?(Ha(N.artifactId,N.label,void 0,o),pt(`Watermark review ready for ${N.label}`)):{ok:!1,message:N.message}}if(!y.mcpTool)return{ok:!1,message:`${y.command} is available from its workspace.`};if(y.mcpTool.tool==="download_video"&&!c)return{ok:!1,message:"Open a notebook before downloading media."};const R=mt(d,y.params),V={...Ub(y.mcpTool.adapter,R),...y.mcpTool.injectParams??{}};if(y.mcpTool.autoInject?.includes("book_id")&&(V.book_id=i),y.mcpTool.autoInject?.includes("notebook_id")&&c&&(V.notebook_id=c.id),S&&S.confirmation!=="none")return await Ce(S.id,V,void 0,void 0,o),{ok:!0,message:"Review the action before running it"};const X=await w(y.mcpTool.tool,V,{chat:o});return await gi(y.mcpTool.tool,X,V,y.command,o)}catch(n){return{ok:!1,message:n instanceof Error?n.message:String(n)}}},yu=async(e,t)=>{const o=qe;if(e.handler.kind!=="tool"){if(e.handler.kind==="ui"&&e.handler.action==="open_actions")return await Ce(),{message:"Actions opened"};const a=await bi(e,t);if(a){if(!a.ok)throw new Error(a.message);return Xe(p=>p===o?null:p),{message:a.message}}const l=Object.keys(e.inputSchema.properties??{}).map(p=>t[p]).filter(p=>p!=null).map(p=>Array.isArray(p)?p.join(" "):String(p)).join(" "),u=e.command==="/export-sequence"?`/export-sequence --aspect ${String(t.aspect??"16:9")} --captions ${String(t.captions??"burned")}`:`${e.command}${l?` ${l}`:""}`,d=await fs(u);if(!d.ok)throw new Error(d.message);return Xe(p=>p===o?null:p),{message:d.message}}const n=e.handler.tool;if(n==="delete_asset"&&t.forget===!0){const a=H.find(u=>u.artifactId===t.asset_id);if(!a)throw new Error("Choose media from the current project.");const l=await Sd({...a,errorMessage:null,lastUsedAt:null,owningBookId:i,owningBookName:uo?.name??i},!0);if(!l.ok)throw new Error(l.message);return Xe(null),{message:l.message}}if(n==="create_book"||n==="rename_book"||n==="delete_book"){const a=n==="create_book"?await La(String(t.name??"")):n==="rename_book"?await Fa(String(t.book_id??i),String(t.name??"")):await Da(String(t.book_id??i),String(t.confirm_name??""));if(!a.ok)throw new Error(a.error);return{message:`${e.title} complete`}}const r=await w(n,t);if(D(r)?.kind==="chat-action-plan"){const a=await Kn(Ts(r),String(t.prompt??""));if(!a.ok)throw new Error(a.message);return Xe(null),{message:a.message}}if(n==="get_notebook"&&typeof t.notebook_id=="string")return await F(String(t.book_id??i),t.notebook_id),Qt("notebook"),Xe(null),{message:"Notebook opened"};if(D(r)?.planVersion===1&&Array.isArray(D(r)?.stages)){const a=await Xt(ft(r));if(!a.ok)throw new Error(a.message);return Xe(null),{message:a.message}}const s=await gi(n,r,t,e.title);if(!s.ok)throw new Error(s.message);return{message:s.message,value:r}},Iu=async(e,t)=>{if(e.confirmation==="generation"&&e.handler.kind==="tool"){const o=D(await w("estimate_cost",{calls:[{tool_name:e.handler.tool,input:t}]})),n=D(o?.estimate),r=Array.isArray(n?.warnings)?n.warnings.filter(u=>typeof u=="string"):[],s=typeof n?.usd=="number"?n.usd:null,a=Gi(r);return{cost:s!==null&&s>0&&(r.length===0||a)?`Estimated cost: $${s.toFixed(4)}`:"Cost estimate unavailable",message:`This action may send your prompt and selected media to a generation provider and incur charges.${r.length?` ${r.join(" ")}`:""} Confirm to start.`}}return{message:e.confirmation==="external"?`${e.title} sends the selected content outside this workspace. Review the destination and content before confirming.`:`${e.title} changes or removes the selected content. Review the target and values before confirming.`}},Cu=async(e,t,o)=>{if(t?.action){const r=Et.find(l=>l.id===t.action?.id);if(!r)return{ok:!1,message:"Reload Actions and choose the command again.",nextInput:e};if(r.handler.kind==="ui"&&(r.handler.action==="open_post_dropbox"||r.handler.action==="open_post_icloud")){const l=e.trim().slice(r.command.length).trim();return cs(l||void 0,r.handler.action==="open_post_dropbox"?"dropbox":"icloud",o)}if(r.handler.kind==="tool"&&r.handler.tool==="transcribe"){const l=or([r],[]).find(S=>S.command===r.command),u=ar(e.trim().slice(r.command.length).trim(),Uo),d=l?mt(u,l.params):{},p=_(d.asset_id)?.trim(),v=_(t.action.values?.asset_id)?.trim();return sn({assetRef:p||v||void 0,languageCode:_(t.action.values?.language_code)??"",diarize:typeof t.action.values?.diarize=="boolean"?t.action.values.diarize:!0,tagAudioEvents:typeof t.action.values?.tag_audio_events=="boolean"?t.action.values.tag_audio_events:!0,chat:o})}const s=or([r],[]).find(l=>l.command===r.command),a=ar(e.trim().slice(r.command.length).trim(),Uo);return await Ce(r.id,{...t.action.values,...mt(a,s.params)},void 0,void 0,o),{ok:!0,message:"Action options opened"}}const n=await fs(e,t,o);return qs(e)||e.trim().toLowerCase()==="/cancel"?jr.current?.(gl(e,n)):ua.current?.(e,n.message),n},Su=async(e,t,o)=>{const n=(e.subjectMap?.subjects??[]).filter(u=>o.subjectIds.includes(u.id)),r=hg(t),s=vg(r,Uo);if(!s.ok)return{ok:!1,message:s.error,nextInput:t,selectInput:!1};if(s.artifactIds.includes(e.asset.artifactId))return{ok:!1,message:"Mention a different image as the replacement.",nextInput:t,selectInput:!1};if(s.artifactIds.length>0||Object.keys(o.replacements).length>0){const u=yg(o.regions,n),d=Ig(u,o.replacements,s.artifactIds);if(!d.ok)return{ok:!1,message:d.error,nextInput:t,selectInput:!1};const p=rb(t,r).replace(/\s+/g," ").trim();return await Gn(e,{operation:"replace",subjectIds:n.map(S=>S.id),...p?{prompt:p}:{},regions:Cg(u,d.replacements),...o.model?{model:o.model}:{}})?{ok:!0,message:`Region replacement queued for ${u.length} ${u.length===1?"region":"regions"}.`}:{ok:!1,message:"The image replacement was not queued.",nextInput:t,selectInput:!1}}return o.subjectIds.length===0&&o.regions.length===0?t.trim()?await Gn(e,{operation:"whole_image",subjectIds:[],prompt:t,...o.model?{model:o.model}:{}})?{ok:!0,message:"Whole-image edit queued."}:{ok:!1,message:"The whole-image edit was not queued.",nextInput:t,selectInput:!1}:{ok:!1,message:"Describe the whole-image edit first.",nextInput:t,selectInput:!1}:o.subjectIds.length>0&&e.subjectMap?.status!=="ready"?{ok:!1,message:e.subjectMap?.status==="analyzing"?"Wait for people and object analysis to finish before editing.":"Analyze the image before editing subjects, or draw a region to edit.",nextInput:t,selectInput:!1}:await Gn(e,{operation:"edit",subjectIds:n.map(u=>u.id),prompt:t,...o.regions.length>0?{editRegions:o.regions.map(u=>u.box)}:{},...o.model?{model:o.model}:{}})?{ok:!0,message:`Image edit queued for ${o.regions.length+n.length} selected areas.`}:{ok:!1,message:"The image edit was not queued.",nextInput:t,selectInput:!1}},wi=e=>(/^\/(?:apply|cancel)(?:\s|$)/iu.test(e)&&(E||ue||he)||((E||ue||he)&&Fe(),Z(null),Le(null),kt(null),jo(null),Xe(null),Y&&Kt(),Do(null)),ma(e)),ms=async(e,t)=>{const o=t?.chat??(qs(e)||e.trim().toLowerCase()==="/cancel"?ma(e):void 0);o?.working();try{const n=await Cu(e,t,o);return o?.finish({...n,...e.trim().toLowerCase()==="/cancel"&&n.ok?{status:"cancelled"}:{}}),n}catch(n){const r={ok:!1,message:n instanceof Error?n.message:String(n)};return o?.finish(r),r}},Ao=e=>{hc(t=>t?.row===e?.row&&t?.column===e?.column?t:e)},hi=(e,t)=>{const o=Oo.current?.screenToFlowPosition({x:e,y:t});if(!o)return null;const n=pg(o,Tt);return n?vt.some(r=>r.row===n.row&&r.column===n.column)?null:n:null},vi=(e,t)=>G?null:hi(e,t),xu=e=>{b!=="notebook"||!Dt(e.dataTransfer)||Fo(!0)},Eu=e=>{if(b!=="notebook"||!Dt(e.dataTransfer))return;const t=e.relatedTarget;t instanceof Element&&e.currentTarget.contains(t)||(Fo(!1),Ao(null))},Au=e=>{Dt(e.dataTransfer)&&e.preventDefault()},_u=e=>{Dt(e.dataTransfer)&&(Fo(!1),Ao(null))},Ru=e=>{!Dt(e.dataTransfer)||e.defaultPrevented||(e.preventDefault(),b==="notebook"&&h("Drop one image, video, or audio file on an open grid square","error"))},Pu=e=>{if(!Dt(e.dataTransfer))return;const t=e.relatedTarget;t instanceof Element&&e.currentTarget.contains(t)||Ao(null)},Mu=e=>{if(e.preventDefault(),Dt(e.dataTransfer)){Gt(null),Fo(!0);const o=vi(e.clientX,e.clientY);Ao(o),e.dataTransfer.dropEffect=o?"copy":"none";return}Ao(null);const t=Oo.current?.screenToFlowPosition({x:e.clientX,y:e.clientY});t&&Gt(fl(t))},Tu=e=>{if(e.preventDefault(),Dt(e.dataTransfer)){if(e.stopPropagation(),Gt(null),Fo(!1),Ao(null),G){h("Wait for the current operation to finish","error");return}const n=[...e.dataTransfer.files];if(n.length!==1){h("Drop one image, video, or audio file per square","error");return}const r=vi(e.clientX,e.clientY);if(!r){h("Choose an open grid square for the media file","error");return}ts(r,n[0]);return}const t=e.dataTransfer.getData("application/x-videobook-cell");if(!mg(t))return;const o=Oo.current?.screenToFlowPosition({x:e.clientX,y:e.clientY});Gt(null),es(t,o)},Qt=e=>{gt(null),Vt(null),ho(),z&&zn(),tt(e),e==="settings"&&ln(),e==="jobs"&&i&&F(i,c?.id).catch(t=>{h(t instanceof Error?t.message:String(t),"error")})},ju={ready:g.state==="ready",states:xr,onFile:(e,t)=>{Wa(e,t)},onFileError:Zo,onOpenLibrary:Eo},yi=z?c?.cells.find(e=>e.id===z.cellId):void 0,qt=yi?Ft(yi.type):z?.cellId===null?"all":null,Jn=z?{...z,uploading:z.cellId!==null&&xr[z.cellId]?.operation==="upload",mode:fe.state.mode,reference:fe.state.reference,referenceStartSeconds:fe.state.startSeconds,referenceDurationSeconds:fe.state.durationSeconds,preparingReference:fe.state.preparing,error:fe.state.error??z.error}:null,$u=e=>{ke(t=>t&&{...t,draftQuery:e})},qu=e=>{if(!z||fe.state.mode===e)return;const t=z.cellId;_e.current+=1,fe.lifecycle.changeMode(e),ke(o=>o&&o.cellId===t?{...o,page:e==="text"?o.page:{...mr,total:o.assets.length},error:null,loading:!1,loadingMore:!1,preparingIndex:!1}:o),e==="text"&&Ct(t,z.draftQuery,0,!1,{mode:e,reference:null,referenceStartSeconds:"0",referenceDurationSeconds:""})},Nu=async e=>{if(!z||fe.state.mode==="text"||!i)return;const t=z;_e.current+=1;const o=fe.state.mode;ke(r=>r&&r.cellId===t.cellId?{...r,error:null,loading:!1,loadingMore:!1,preparingIndex:!1}:r);const n=await fe.lifecycle.prepare(o,()=>ng(e,i,Fg(o)));if(n.status==="error"){h(n.error,"error");return}n.status!=="stale"&&await Ct(t.cellId,"",0,!1,{mode:n.mode,reference:n.reference,referenceStartSeconds:"0",referenceDurationSeconds:""})},Lu=async e=>{if(!z)return;const t=z;_e.current+=1;const o=e.type==="image"?"image-reverse":"video-reverse";ke(r=>r&&r.cellId===t.cellId?{...r,error:null,loading:!1,loadingMore:!1,preparingIndex:!1}:r);const n=await fe.lifecycle.prepare(o,()=>og(w,{sourceBookId:e.owningBookId,sourceArtifactId:e.artifactId,mode:o,previewUrl:o==="image-reverse"?e.thumbnailUrl??e.mediaUrl:e.mediaUrl}));if(n.status==="error"){h(n.error,"error");return}n.status!=="stale"&&await Ct(t.cellId,"",0,!1,{mode:n.mode,reference:n.reference,referenceStartSeconds:"0",referenceDurationSeconds:""})},Fu=()=>{z&&(_e.current+=1,fe.lifecycle.clearReference(),ke(e=>e&&{...e,error:null,loading:!1,loadingMore:!1,preparingIndex:!1}))},Du=async()=>{if(!z||!qt||qt==="audio")return;const e=z,t=++_e.current;ke(o=>o&&{...o,preparingIndex:!0,error:null});try{const o=await tg({start:()=>w("repair_library_search_indexes",{kinds:qt==="all"?["image","video"]:[qt]}),listJobs:(s,a)=>w("list_jobs",{book_id:s,job_ids:a}),isCancelled:()=>_e.current!==t});if(_e.current!==t)return;const n=_e.current+1;if(await Ct(e.cellId,e.query,0,!1),_e.current!==n)return;if((ie(o?.failed)??0)>0){const s=Array.isArray(o?.failures)?o.failures:[],a=_(D(s[0])?.message),l=`Some media could not be indexed.${a?` ${a}`:""}`;ke(u=>u&&{...u,error:l}),h(l,"error")}else h(`Indexed ${ie(o?.indexed)??0} media assets for Similar search`)}catch(o){if(_e.current!==t)return;const n=o instanceof Error?o.message:String(o);ke(r=>r&&{...r,preparingIndex:!1,error:n}),h(n,"error")}},Ou=()=>{z&&(fe.lifecycle.clearError(),Ct(z.cellId,z.draftQuery,0,!1))},Vu=()=>{z&&Ct(z.cellId,z.query,z.page.offset+z.page.limit,!0)},Gu=e=>{if(!z)return;const t=Zp(z.tagFilters,e);eg(t,z.tagFilters)||Ct(z.cellId,z.query,0,!1,void 0,t)},Uu=()=>{!z||z.tagFilters.length===0||Ct(z.cellId,z.query,0,!1,void 0,[])},Wu=async e=>{if(!z||g.state!=="ready")return;const t=z.cellId;try{const o=await w("suggest_asset_tags",{book_id:i,...e.trim()?{prefix:e.trim()}:{},limit:20},{background:!0}),n=Array.isArray(o?.suggestions)?o.suggestions.flatMap(r=>{const s=r;return typeof s.facet=="string"&&typeof s.key=="string"&&typeof s.label=="string"?[{facet:s.facet,key:s.key,label:s.label,assets:Number(s.assets)||0}]:[]}):[];ke(r=>r&&r.cellId===t?{...r,tagSuggestions:n}:r)}catch{}},Yt=e=>{if(za(e)&&g.state==="ready"){Eo(e);return}Z(e),Le(null),kt(null),ro("selection")&&me(!0)},Ii=e=>{Z(e),kt(null),Le(e),ro("selection")&&me(!0);const t=c?.cells.find(o=>o.id===e);t?.outputArtifactId&&!no(t.type)&&Si(e,t.outputArtifactId)},Ci=(e,t)=>{const o=c?.cells.find(n=>n.id===e);if(o&&!no(o.type)){Ii(e);return}Z(e),Le(null),kt(e),ro("selection")&&me(!0),Si(e,t)},Si=(e,t)=>{if(!i){_n({cellId:e,assetId:t,loading:!1,error:"Book is unavailable",revisions:[]});return}_n({cellId:e,assetId:t,loading:!0,error:null,revisions:[]}),w("asset_history",{asset_id:t,book_id:i,limit:20},{background:!0}).then(o=>{const n=Dg(o);_n(r=>r?.cellId===e&&r.assetId===t?{cellId:e,assetId:t,loading:!1,error:null,revisions:n}:r)}).catch(o=>{_n(n=>n?.cellId===e&&n.assetId===t?{cellId:e,assetId:t,loading:!1,error:o instanceof Error?o.message:String(o),revisions:[]}:n)})},ee=Bt?c?.cells.find(e=>e.id===Bt)??null:null,Re=Bt?Mt.find(e=>e.id===Bt)??null:null,_o=Ye?.target.kind==="slot"?Ye.target.slot:null,ps=Re?wp({type:Re.data.kind,model:Re.data.model,operation:Re.data.operation,outputArtifactId:Re.data.outputArtifactId,tool:Re.data.tool},Re.data.status):null,zu=ee?Ft(ee.type):null,Hu=!!(ee&&Re&&zu&&hp(ee.type,ee.outputArtifactId,Re.data.targetConnectionCount??0)),De=Re?.data.asset&&Re.data.asset.type!=="audio"&&(Re.data.asset.mediaUrl||Re.data.asset.thumbnailUrl)?Re.data.asset:null,Xn=ee?.outputArtifactId&&Re?.data.asset&&Os(Re.data.asset.type)?ee.outputArtifactId:null,Bu=!!(c&&ee&&Xn&&ee.slot.row+1<gn.maximumRowCount&&!vt.some(e=>e.row===ee.slot.row+1&&e.column===ee.slot.column)),gs=Me===Bt?dd:null,Ku=ee&&c&&ee.type!=="goal"?["generate_video","generate_image"].filter(e=>{try{return Hl({actions:Qe,cellId:`context-menu-${e}`,cellType:e,document:c,lastWorkSlot:Ge,sourceCellId:ee.id}),!0}catch{return!1}}):[],He=[];if(ee&&Re){if(ee.type==="post"){const e=G||g.state!=="ready";He.push({id:"save-iphone",label:"Save to iPhone",icon:"upload",disabled:e},{id:"upload-dropbox",label:"Upload to Dropbox",icon:"upload",disabled:e})}He.push({id:"inspect",label:ee.type==="goal"?"Open goal":"Edit cell",icon:"inspect"}),ps&&He.push({id:"run",label:vp(ee.type,ps.label),icon:"run",disabled:G||ps.disabled}),Hu&&He.push({id:"library",label:"Choose media",icon:"library",disabled:G}),De&&ee.type!=="post"&&["video","image","final"].includes(De.type)&&He.push({id:"create-post",label:"Create Post",icon:"inspect",disabled:G||g.state!=="ready"}),De&&He.push({id:"media",label:"Open media",icon:"media"}),De&&(De.type==="video"||De.type==="final")&&(He.push({id:"cold-open",label:"Edit cold open",icon:"split",disabled:G||g.state!=="ready"||!De.mediaUrl}),He.push({id:"download",label:"Download video",icon:"download",disabled:G||g.state!=="ready"||!De.mediaUrl}),He.push({id:"extract_frame",label:"Extract frame",icon:"extract-frame",disabled:G}));for(const e of Ku){const t=e==="generate_video";He.push({id:e,label:t?"Generate video":"Generate image",icon:t?"generate-video":"generate-image",disabled:G})}Xn&&He.push({id:"duplicate",label:"Duplicate",icon:"duplicate",disabled:G||!Bu}),gs&&He.push({id:"split",label:"Split video",icon:"split",disabled:G})}const Qn=[];Ma.size>0&&Qn.push({id:"group_images",label:"Group images here",icon:"group-images",disabled:G});const Ju=e=>{_o&&e==="group_images"&&Ga(_o)},Xu=async()=>{if(!(!Xn||!i||!c)){T(!0);try{const e=D(await w("duplicate_asset",{asset_id:Xn,book_id:i,notebook_id:c.id})),t=_(e?.cell_id),o=_(e?.address);if(!t||!o)throw new Error("The server did not return the duplicated notebook cell");await F(i,c.id),Z(t),ae(),h(`Duplicated as ${o}`)}catch(e){h(e instanceof Error?e.message:String(e),"error")}finally{T(!1)}}},Qu=async e=>{if(!i||!c||!ee)return;const t=c.id,o=ee.id;T(!0);try{const n=ge(await w("get_notebook",{book_id:i,notebook_id:t}));if(!n)throw new Error("The server returned an invalid notebook");const r=Hl({actions:Qe,cellId:xt(),cellType:e,document:n,lastWorkSlot:Ge,sourceCellId:o}),s=await vl({bookId:i,callTool:w,document:n,draft:r,...n.revision?{expectedRevision:n.revision}:{}});Ae(r.cell.slot);const a=await F(i,t);Yt(s.cellId),Yo(s.cellId,void 0,a),io(s.cellId),h(`Added ${s.cellAddress} ${e==="generate_video"?"video":"image"} generation from ${s.sourceAddresses[0]}`)}catch(n){h(n instanceof Error?n.message:String(n),"error")}finally{T(!1)}},Yu=async()=>{if(!i||G||g.state!=="ready"||!De?.mediaUrl)return;const e=De.artifactId;T(!0);try{const t=await Zg(w,"download",i,e);Q.current.bookId===i&&h(t)}catch(t){Q.current.bookId===i&&h(t instanceof Error?t.message:String(t),"error")}finally{Q.current.bookId===i&&me(!0),T(!1)}},Zu=e=>{if(ee){if(e==="save-iphone"||e==="upload-dropbox"){const t=ls(ee.id,e==="upload-dropbox"?"dropbox":"icloud");t.ok||h(t.message,"error");return}if(e==="create-post"){Oa(ee.id);return}if(e==="inspect"){Yt(ee.id);return}if(e==="run"){on(ee.id);return}if(e==="library"){Eo(ee.id);return}if(e==="cold-open"&&De){const t=ss(De.artifactId);t.ok||h(t.message,"error");return}if(e==="download"){Yu();return}if(e==="media"||e==="extract_frame"){De&&Vn(ee,De,Ye?.returnFocus??null);return}if(e==="duplicate"){Xu();return}if(e==="generate_video"||e==="generate_image"){Qu(e);return}if(e==="split"&&gs){cn({sourceReference:gs.source.id,cutPointsSeconds:[]}).then(t=>{t.ok||h(t.message,"error")});return}}},ef=()=>{ee&&xo([ee])},tf=async e=>{if(!i||!c)return;const t=c.cells.find(a=>a.id===e);if(!t)return;const o=dg(t,c.cells,c.edges),n=ug({address:W(t.slot),error:Mt.find(a=>a.id===e)?.data.statusError??"the provider rejected the request",mediaLabel:fg(t.type),producerAddress:o?W(o.slot):null,provider:o?.provider??t.provider??null,model:o?.model??t.model??null});me(!0);const r=wi(n),s=await ms(n,{chat:r});s.ok||h(s.message,"error")},of=async e=>{if(!i||!c||G||g.state!=="ready")return;const t=Mt.find(n=>n.id===e)?.data.statusError;if(!lg(t))return;const o=cg(c,e);if(!o){h("The generator for this failed output is no longer available","error");return}await on(o.id,void 0,void 0,e)},nf={ready:!G&&g.state==="ready",deleteCell:async e=>{const t=c?.cells.find(o=>o.id===e);t&&await xo([t],{confirm:!1})},repairCell:tf,retryCell:of},un=Y?.asset.type==="image"?Y:null,xi=m.useMemo(()=>un?se.filter(e=>e.type.toLowerCase()==="image"&&e.artifactId!==un.asset.artifactId):[],[se,un]),rf=m.useMemo(()=>xi.map(e=>({artifactId:e.artifactId,address:e.cellAddress,label:e.cellAddress,thumbnailUrl:e.thumbnailUrl??e.mediaUrl})),[xi]),Yn=un?`image-edit:${un.key}`:`chat:${i}`,Ro=Cn?.bookId===i&&Cn.session===Yn?Cn:null,sf=hr?.bookId===i&&hr.session===Yn?hr:null,Ei=Ne?.turnId!==void 0&&Ne.turnId===fa.at(-1)?.id,Ai=!!(Ro&&(Ne||Y)),ks=!Qo&&!ve&&!it,af=e=>{if(!U)return;let t=U,o=!1;for(const n of e){if(n.kind==="prompt"){t=tr(t,n.prompt);continue}if(n.kind==="model"){const r=Wo.find(s=>s.id===n.actionId);if(!r)continue;t=Xi(t,r,bt),o=!0;continue}t=xs(t,n.name,n.value),o=!0}yt(t,o)},lf=async e=>{const t=E?.kind==="generation"&&U?{kind:"generation",action:U.action,models:Wo}:E?.kind==="chain-step"?{kind:"chain-step"}:E?.kind==="transcribe"?{kind:"transcribe"}:E||ue||he?{kind:"other"}:{kind:"none"},o=xg(e,t);return o.kind==="refused"?o.outcome:o.kind==="revise"?(af(o.edits),{status:"review",message:"The review on screen is updated. It is still waiting for apply or cancel."}):gl(o.input,await ms(o.input))},Zt=yp({bookId:i,notebookId:c?.id,scope:Yn,available:ks&&g.state==="ready"&&!!i&&!Y&&!Ne&&!ve,disabled:G||!!(he||ue||E),onUserTurn:()=>{he||ue||E||(ka.current=ga(),Z(null),Le(null),kt(null))},onAction:async(e,t)=>{const o=ka.current??ga(),n=()=>t()&&o.isCurrent();if(!n())return{status:"cancelled",message:"A newer message replaced this request."};if(G||E||ue||he)return{status:"failed",message:"Finish the current command or use Apply or Cancel on screen first."};const r=Ts(e.plan);if(r.bookId!==i)return{status:"cancelled",message:"The project changed. Repeat the command here."};const s=await Kn(r,e.prompt,n,o);return n()?(h(s.message,s.ok?"info":"error"),{status:s.ok?s.nextInput?.startsWith("/apply")?"review":/queued|started|running|processing/i.test(s.message)?"queued":"completed":"failed",message:s.message}):{status:"cancelled",message:"Workspace changed. Check the previous project for accepted work."}},onReviewCommand:lf});m.useLayoutEffect(()=>{jr.current=Zt.reportOutcome,ua.current=Zt.shareTypedTurn,$r.current=Zt.active},[Zt.active,Zt.reportOutcome,Zt.shareTypedTurn]),Ip(`${b}:${i}:${c?.id??""}`,ks&&g.state==="ready"&&!G&&(!!i||!!Ro));const cf=()=>{Y||Kc()},_i=(()=>{if(he){const s=he,a=s.includeQr&&s.includeHandle?"Add handle and QR to the video":s.includeQr?"Add a QR code to the video":"Add a handle to the video";return C.jsx(ot,{kind:"watermark",ariaLabel:"Watermark review",tag:"WATERMARK · CHAT",title:a,address:s.targetLabel,effect:{label:"Rebuilds playable proxy",tone:"default"},validation:Sp({...s,handle:s.identities[s.platform].handle}),busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Bb,{busy:G,state:s,onChange:({handle:l,...u})=>{nl(i,s.platform,{handle:l,...u}),Te(d=>d&&{...d,...u,identities:l===void 0?d.identities:{...d.identities,[d.platform]:{...d.identities[d.platform],handle:l}},error:null})},onMediaMetadata:l=>Te(u=>u&&{...u,...u.durationSeconds===null?Cp(u,l.durationSeconds):{},durationSeconds:l.durationSeconds,width:l.width,height:l.height})})})}if(ue){const s=ue.plan,a=Object.values(ue.previews),l=a.reduce((p,v)=>p+v.warnings.length,0),u=`${s.stages.length} stage${s.stages.length===1?"":"s"}`,d=l>0?` · ${l} warning${l===1?"":"s"}`:"";return C.jsx(ot,{kind:"plan",ariaLabel:"Command plan review",tag:`PLAN · ${s.sourceSurface.toUpperCase()}`,title:s.summary,effect:{label:`${u}${d}`,tone:l>0?"warning":"default"},validation:xp({suggestions:s.suggestions,previews:a}),busy:G,applyFormId:nt,onCancel:Fe,secondaryActions:qr?C.jsxs("button",{type:"button",className:"confirm-sheet-secondary",disabled:G,onClick:()=>{Yd()},children:[C.jsx(mb,{size:13,"aria-hidden":"true"}),"Restore last edit"]}):null,children:C.jsx(Jk,{busy:G,plan:s,previews:ue.previews,onToggleSuggestion:p=>{Xd(p)}})})}if(!E)return null;if(E.kind==="transcribe"){const s=E,a=new Map(se.map(p=>[p.artifactId,p.cellAddress])),l=Ep(H,a),u=l.find(p=>p.artifactId===s.assetId)??null,d=p=>{O(v=>v?.kind==="transcribe"?{...v,...p}:v)};return C.jsx(ot,{kind:"transcribe",ariaLabel:"Transcribe review",tag:"TRANSCRIBE · CHAT",title:u?`Transcribe ${u.label}`:"Transcribe a clip",address:u?.label??null,effect:{label:"Queues 1 transcription",tone:"default"},validation:rl({assetId:s.assetId,languageCode:s.languageCode}),busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Xk,{busy:G,clip:u,choices:l,languageCode:s.languageCode,diarize:s.diarize,tagAudioEvents:s.tagAudioEvents,estimateUsd:s.estimateUsd,estimateLoading:s.estimateLoading,estimateUnavailable:s.estimateUnavailable,onClipChange:p=>{d({assetId:p,estimateUsd:null,estimateLoading:p!==null,estimateUnavailable:!1}),p?Un(p,s.languageCode,s.diarize,s.tagAudioEvents):To.current+=1},onLanguageChange:p=>d({languageCode:p}),onDiarizeChange:p=>{d({diarize:p,estimateUsd:null,estimateLoading:s.assetId!==null,estimateUnavailable:!1}),s.assetId&&Un(s.assetId,s.languageCode,p,s.tagAudioEvents)},onTagAudioEventsChange:p=>{d({tagAudioEvents:p,estimateUsd:null,estimateLoading:s.assetId!==null,estimateUnavailable:!1}),s.assetId&&Un(s.assetId,s.languageCode,s.diarize,p)}})})}if(E.kind==="generation"){const s=E,a=zo[0];return C.jsx(ot,{kind:"generation",ariaLabel:"Generation action review",tag:"GENERATION · CHAT",title:s.summary,address:a?`@${a.address}`:null,effect:{label:"Queues 1 job · new cell",tone:"default"},validation:Ap({prompt:s.draft.cell.prompt,previewLoading:s.previewLoading,previewError:s.previewError,settingsError:Pp(s.draft.action.model,sl(s.draft),zo),previewStale:s.previewStale,promptLeaks:Rp(s.preview).promptLeaks,estimateUnknown:_p(s.preview).unknown}),busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Qk,{actions:Wo,busy:G,draft:s.draft,modes:jc,preview:s.preview,previewError:s.previewError,previewLoading:s.previewLoading,previewStale:s.previewStale,sources:zo,sourceOptions:$c,voiceCatalog:Hn,promptHistory:ed,onActionChange:td,onAddSource:ad,onModeChange:od,onPromptChange:Pa,onRefreshPreview:rd,onRemoveSource:id,onSelectSource:sd,onSettingChange:nd})})}if(E.kind==="post-delivery"){const s=E.review,a=dn.find(p=>p.id===s.postId)??null,l=c?.cells.find(p=>p.id===s.postId),u=l?.outputArtifactId?re.get(l.outputArtifactId)??null:null,d=s.destination==="icloud";return C.jsx(ot,{kind:"post-delivery",ariaLabel:"Post delivery",tag:"DELIVER",title:d?"Save to iPhone":"Upload to Dropbox",address:a?.address??null,effect:{label:d?"iCloud · shared folder":"Leaves workspace · private",tone:d?"default":"warning"},validation:al(a,s),busy:G,busyLabel:d?"Saving to iPhone…":"Uploading to Dropbox…",applyLabel:"Upload",applyFormId:nt,onCancel:Fe,children:a&&C.jsx(Yk,{post:a,asset:u,review:s,busy:G,onCopyChange:p=>ut({copy:p}),onLanguage:p=>gu(a,s,p),onRegen:()=>ku(a,s),onFolderChange:p=>ut(d?{icloudFolder:p}:{dropboxFolder:p}),onDestination:bu,onConnect:()=>{pu()},onCheckConnection:()=>{is()},onOpenPost:()=>Yt(a.id),onLink:async p=>{await w("link_post",{book_id:s.bookId,post_cell_id:a.id,...p}),await F(s.bookId,s.notebookId),Fe()}})})}if(E.kind==="cold-open"){const s=E.review,a=s.suggestion;return C.jsx(ot,{kind:"cold-open",ariaLabel:"Cold-open review",tag:"COLD OPEN",title:"Highlight, then the full clip",address:s.label,effect:{label:"New video copy",tone:"default"},validation:{blocking:a?Mp(a.startSeconds,a.endSeconds,a.durationSeconds):null,notice:null},busy:G,busyLabel:a?"Creating copy…":"Finding highlight…",applyLabel:a?"Create copy":"Find highlight",applyFormId:nt,onCancel:Fe,children:C.jsx(Zk,{review:s,disabled:G,onChange:(l,u)=>O(d=>d?.kind==="cold-open"&&d.review.suggestion?{...d,review:{...d.review,requestId:xt(),suggestion:{...d.review.suggestion,startSeconds:l,endSeconds:u}}}:d)})})}if(E.kind==="split"&&$a){const s=$a,a=Tp({cutPointsSeconds:s.cutPointsSeconds,sourceDurationSeconds:s.sourceDurationSeconds});return C.jsx(ot,{kind:"split",ariaLabel:"Video split review",tag:"SPLIT VIDEO · CHAT",title:$p({pieces:a,selectedIndex:s.selectedIndex}),address:s.sourceLabel,effect:{label:s.outputMode==="all"?`${a.length} new clip${a.length===1?"":"s"} · source preserved`:"New clip · source preserved",tone:"default"},validation:jp({availableEmptyCells:s.availableEmptyCells,cutPointsSeconds:s.cutPointsSeconds,outputMode:s.outputMode,sourceDurationSeconds:s.sourceDurationSeconds}),busy:G,applyLabel:"Apply split",applyFormId:nt,hints:C.jsxs("span",{children:[C.jsx("kbd",{children:"← →"})," 0.1s · ",C.jsx("kbd",{children:"⇧← →"})," 1s · ",C.jsx("kbd",{children:"⌥← →"})," 0.01s on the focused bound · ",C.jsx("kbd",{children:"↵"})," apply · ",C.jsx("kbd",{children:"Esc"})," cancel"]}),onCancel:Fe,children:C.jsx(eb,{cutPointsSeconds:s.cutPointsSeconds,mediaUrl:s.mediaUrl,outputMode:s.outputMode,selectedIndex:s.selectedIndex,sourceDurationSeconds:s.sourceDurationSeconds,sourceFps:s.sourceFps,onChange:Zc})})}if(E.kind==="routed"){const s=E.plan,a=Tc,l=a?.settings.find(d=>d.label==="Source")?.value,u=`CHAT · ${s.routedTool.toUpperCase()}`;return fo?C.jsx(ot,{kind:"post",ariaLabel:"Chat action review",tag:u,title:a?.title??"Post to X",address:fo.sourceLabel,effect:a?.effect??null,validation:fo.validation,busy:G,busyLabel:"Posting…",applyLabel:"Post to X",applyFormId:nt,onCancel:Fe,children:C.jsx(tb,{asset:fo.asset,busy:G,draft:fo.draft,prompt:s.prompt,settings:a?.settings??[],sourceLabel:fo.sourceLabel,threadReview:E.xPostReview,connection:$o,onChange:Jc,onConnect:()=>{ns()},onThreadOptionsChange:Xc,onThreadCreditsChange:Yc,onThreadPromptChange:Qc})}):C.jsx(ot,{kind:"routed",ariaLabel:"Chat action review",tag:u,title:a?.title??s.summary,address:l?.startsWith("@")?l:null,effect:a?.effect??null,validation:_s,busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Ml,{prompt:s.prompt,settings:a?.settings??[],speedPreview:ha})})}if(E.kind==="chain-step"){const s=qp(E.review,E.remaining);return C.jsx(ot,{kind:"routed",ariaLabel:"Chain step review",tag:`CHAIN · ${E.review.tool.toUpperCase()}`,title:s.title,address:E.review.address,effect:s.effect,validation:_s,busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(Ml,{prompt:s.postText??"",settings:s.settings,speedPreview:null})})}const e=E,t=e.kind==="notebook"?e.plan.summary:e.summary,o=e.kind==="notebook"?e.plan.reason:e.reason,n=e.kind==="notebook"?`${e.plan.action.kind} notebook cell`:e.kind==="split"?"Split video":e.command.frameMode==="time"?`Extract frame at ${e.command.timestampSeconds??0}s`:`Extract ${e.command.frameMode} frame`,r=e.kind==="notebook"?"Edits the notebook graph":e.kind==="frame"?"New image cell":"New clips · source preserved";return C.jsx(ot,{kind:e.kind,ariaLabel:"Chat action review",tag:"NOTEBOOK · CHAT",title:t,effect:{label:r,tone:"default"},validation:_s,busy:G,applyFormId:nt,onCancel:Fe,children:C.jsx(ob,{kindLabel:e.kind.toUpperCase(),reason:o,stageTitle:n})})})(),fn=m.useMemo(()=>{const e=H.map(a=>{const l=c?.cells.find(u=>u.outputArtifactId===a.artifactId);return{value:a.artifactId,label:l?`${W(l.slot)} · ${a.label}`:a.label,detail:a.type}}),t=c?.cells.map(a=>({value:a.id,label:`${W(a.slot)} · ${a.label??a.type}`}))??[],o=J?.tracks.map(a=>({value:a.trackId,label:a.name,detail:a.kind}))??[],n=J?.clips.map(a=>({value:a.clipId,label:`${a.source.kind} · frame ${a.timelineStartFrame}`,detail:J.tracks.find(l=>l.trackId===a.trackId)?.name}))??[],r={book_id:x.map(a=>({value:a.bookId,label:a.name})),notebook_id:c?[{value:c.id,label:c.name}]:[],cell_id:t,cell:t,source_cell_id:t,target_cell_id:t,clip_id:n,clip_ids:n,narration_clip_id:n,track_id:o,track_ids:o,audio_track_id:o,artifact_id:e,artifact_ids:e,artifact_ref:e,asset_id:e,asset_ref:e,source_artifact_id:e};for(const a of["image","audio","video"]){const l=e.filter(u=>u.detail===a||a==="video"&&u.detail==="final");r[`${a}_ref`]=l,r[`${a}_refs`]=l,r[`${a}_artifact_id`]=l,r[`${a}_asset_id`]=l,r[`${a}_asset_ids`]=l}for(const a of["source_asset_id","target_asset_id","first_asset_id","second_asset_id","additional_asset_ids","output_artifact_id","replacement_artifact_id","expected_output_artifact_id","exclude_artifact_ids"])r[a]=e;for(const a of["osg_asset_id","card_asset_id","qr_image_refs","character_image_refs","first_frame_ref","last_frame_ref","end_frame_ref"])r[a]=r.image_ref;return r.motion_video_refs=r.video_ref,r.layer_asset_id=r.audio_ref,r.sound_effect_ref=r.audio_ref,r.source_script_id=e.filter(a=>a.detail==="script"),r.cell_ids=t,r.audio_id=n,r.outgoing_clip_id=n,r.incoming_clip_id=n,r.source_book_id=r.book_id,r.target_book_id=r.book_id,r.edge_id=c?.edges.map(a=>({value:a.id,label:`${t.find(l=>l.value===a.source)?.label??a.source} → ${t.find(l=>l.value===a.target)?.label??a.target} · ${a.targetInput}`}))??[],{bookId:i,notebookId:c?.id,sequenceId:J?.sequenceId,sequenceRevision:J?.revision,cellId:$?.id,assetId:$?.outputArtifactId,choices:r,cellIds:It.map(a=>a.id),assetIds:It.flatMap(a=>a.outputArtifactId?[a.outputArtifactId]:[]),media:Object.fromEntries(H.map(a=>[a.artifactId,{url:a.mediaUrl,type:a.type,width:a.width,height:a.height,objectHash:a.objectHash}]))}},[H,i,x,c,$,It,J]),df=m.useMemo(()=>Np(In,!!(ue||E||he)),[In,ue,E,he]),bs=(e,t=et.frame)=>{J&&(Z(e),Ue(null),wt.load(),et.seek(t),Tn({bookId:i,cellId:e,initialFrame:t,returnFocus:document.activeElement instanceof HTMLElement?document.activeElement:null}))},Ri=()=>{et.closePicker(),wt.stop(),Tn(null)},ws={sequence:J,assets:H,assembly:Qo?{...et,picker:null}:et,disabled:G||g.state!=="ready",frame:et.frame,onSeek:bs,onPreview:bs,onExport:()=>{fs("/export-sequence").then(e=>{e.ok||h(e.message,"error")})},onRemove:e=>{const t=c?.cells.find(o=>o.id===e);t&&xo([t])}},mn=Jn&&(Jn.cellId===null||$?.id===Jn.cellId&&!$.outputArtifactId)?Jn:null,hs=mn&&qt?C.jsx(hf,{disabled:G||g.state!=="ready",state:mn,kind:qt,accept:qt==="all"?Object.values(il).join(","):il[qt],targetBookId:i,onClose:Dd,onMode:qu,onDraftQuery:$u,onSearch:Ou,onLoadMore:Vu,onAttach:e=>{Od(e)},onUpload:e=>{if(mn.cellId){Wa(mn.cellId,e);return}const t=Rs(e);if(!(!t||!c))try{const o=z?.slot??Mo(t,c.cells,Ge);ts(o,e)}catch(o){h(o instanceof Error?o.message:String(o),"error")}},onReferenceFile:e=>{Nu(e)},onClearReference:Fu,onReferenceStart:fe.lifecycle.setStartSeconds,onReferenceDuration:fe.lifecycle.setDurationSeconds,onSimilar:e=>{Lu(e)},onRepairIndexes:()=>{Du()},onToggleTagFilter:Gu,onClearTagFilters:Uu,onTagQuery:e=>{Wu(e)}}):null,uf=mn?.cellId===null&&hs?C.jsxs("div",{className:"composer-notebook-dock inspector",children:[C.jsxs("header",{children:[C.jsxs("span",{className:"inspector-cell-title",children:[C.jsx($l,{size:15}),C.jsx("strong",{children:"Library"})]}),C.jsx("div",{className:"inspector-header-actions",children:C.jsx($i,{})})]}),hs]}):null,vs=$?.type==="goal"?Ia.get($.id)??null:null,ff=!Qo&&$?.type==="goal"?vs?C.jsx(cb,{goal:vs,connected:g.state==="ready",onAction:vd,onPreview:yd,onSelectCell:Yt,resolveAsset:e=>re.get(e)??null,onPreviewCell:e=>{const t=c?.cells.find(n=>n.id===e),o=t?.outputArtifactId?re.get(t.outputArtifactId):null;t&&o&&Vn(t,o)}},vs.goalId):C.jsx(db,{}):null,ys=uf??ff??(!Qo&&ce&&$&&$.type!=="timeline"?C.jsxs("div",{className:["composer-notebook-dock","inspector",Sr.has(ce.id)?"inspector-deleting":""].filter(Boolean).join(" "),children:[C.jsxs("header",{children:[C.jsxs("span",{className:"inspector-cell-title",title:Ps(ce.data.kind),children:[C.jsx(vf,{kind:ce.data.kind}),C.jsx("strong",{children:Ps(ce.data.kind)}),C.jsx("code",{className:"inspector-cell-address",children:W($.slot)}),(Yr?.kind==="queued"||Yr?.kind==="generating")&&C.jsx("span",{className:"inspector-generating-badge",role:"status",children:Yr.kind==="queued"?"Queued":"Generating"})]},ce.id),C.jsxs("div",{className:"inspector-header-actions",children:[$.outputArtifactId&&no($.type)&&C.jsx("button",{type:"button",className:zt===ce.id?"inspector-source-toggle active":"inspector-source-toggle",title:zt===ce.id?"View cell":"View history","aria-label":zt===ce.id?"View cell":"View history","aria-pressed":zt===ce.id,onClick:()=>{if(zt===ce.id){kt(null);return}Ci(ce.id,$.outputArtifactId)},children:C.jsx(pb,{size:15})}),!an&&C.jsx("button",{type:"button",className:["inspector-source-toggle",no($.type)?"":"inspector-source-toggle-labeled",Wt===ce.id?"active":""].filter(Boolean).join(" "),title:Wt===ce.id?"View cell":"View source","aria-label":Wt===ce.id?"View cell":"View source","aria-pressed":Wt===ce.id,onClick:()=>{if(Wt===ce.id){Le(null);return}Ii(ce.id)},children:no($.type)?C.jsx(gb,{size:15}):C.jsxs(C.Fragment,{children:[C.jsx(kb,{size:13,"aria-hidden":"true"}),C.jsx("span",{children:"Source"})]})}),$.type.startsWith("generate_")&&C.jsx("span",{className:"composer-dock-close-divider","aria-hidden":"true"}),C.jsx("div",{ref:ac,className:"inspector-header-action-host"}),C.jsx($i,{label:$.type.startsWith("generate_")?"Close":void 0,shortcut:$.type.startsWith("generate_"),divider:!$.type.startsWith("generate_")})]})]}),hs??(an?C.jsx(yf,{post:an,cells:c?.cells??[],asset:ce.data.asset,bookId:i,call:g.state==="ready"?w:void 0,onRefresh:()=>F(i,c?.id),onSelectCell:Yt,onDeliver:e=>{const t=ls(an.id,e);t.ok||h(t.message,"error")},onReviewX:fu,onDelete:()=>{xo([$])}},an.id):C.jsx(ib,{headerActionHost:sc,notebookId:c?.id??"",bookId:i,assetTools:g.state==="ready"?w:void 0,cell:$,cells:c?.cells??[],edges:c?.edges??[],asset:ce.data.asset,cellAssets:nn,versionAssets:cd,status:ce.data.status,error:Ta,queuedCellIds:An,runErrors:ao,jobs:ja,onCancelJob:Ba,generationActions:Qe,mentionAssets:se,voiceCatalog:Hn,busy:G||!!ud?.operation,deleting:Sr.has($.id),sourceVisible:Wt===$.id,historyVisible:zt===$.id,history:lo&&lo.cellId===$.id&&lo.assetId===$.outputArtifactId?{revisions:lo.revisions,loading:lo.loading,error:lo.error}:zt===$.id||Wt===$.id&&$.outputArtifactId?{revisions:[],loading:!0,error:null}:void 0,onUpdate:Pd,onSetInput:Md,onRun:on,onDelete:Td,onOpenFullscreen:(e,t)=>{Vn($,e,void 0,t)},onPreviewPayload:fd,initialGenerationPreview:Ca?.cellId===$.id?Ca:void 0,onSelectSource:Z,onLoadGenerationPayload:md,onInspectGenerationRequest:pd,onDownloadGenerationHar:gd,onOpenSettings:()=>Qt("settings"),mediaInsightWork:na,onTranscribeAsset:xd,onLoadTranscriptJson:bd,onDownloadTranscriptSrt:wd},`${$.id}:${$.prompt??""}`))]}):null),mf=Sg({musicSession:!!ve,cellInspector:!!ys}),pf=ys||ve?C.jsx("div",{hidden:!!ve,inert:ve?!0:void 0,children:ys}):null;return C.jsxs("main",{className:`app-shell app-screen-${b} ${Y?"media-fullscreen-open":""}`,onDragEnter:xu,onDragLeave:Eu,onDragOver:Au,onDropCapture:_u,onDrop:Ru,onKeyDownCapture:e=>{e.defaultPrevented||(e.ctrlKey||e.metaKey)&&e.shiftKey&&e.key.toLowerCase()==="k"&&!e.nativeEvent.isComposing&&(e.preventDefault(),e.stopPropagation(),Ce())},children:[C.jsxs("header",{className:"topbar",children:[C.jsx("div",{className:"topbar-book-controls",children:C.jsx("div",{className:"brand-project",children:C.jsxs("div",{className:"brand-project-trigger",children:[C.jsxs("button",{type:"button",className:"brand-project-home","data-composer-focus":"return",title:"Open notebook",onClick:()=>Qt("notebook"),children:[C.jsx(bb,{size:18}),C.jsx("span",{children:"/videobook"})]}),C.jsx(If,{activeBook:uo,books:x,disabled:G||g.state!=="ready",error:xc,loading:Sc,open:Cc,onCreate:La,onDelete:Da,onOpenChange:Jt,onRefresh:Rd,onRename:Fa,onSelect:Na})]})})}),b==="notebook"&&c&&C.jsx(Cf,{busy:G||g.state!=="ready",arrangeDisabled:G||g.state!=="ready"||c.cells.length===0,selectedCount:It.length,activeAddress:$?W($.slot):null,onAdd:es,onAddDragEnd:()=>Gt(null),onArrange:qd,onDeleteSelection:Va,onSelectionActions:()=>{Ce(void 0,{cell_id:$?.id,cell_ids:It.map(e=>e.id),artifact_ids:It.flatMap(e=>e.outputArtifactId?[e.outputArtifactId]:[])})},onClearSelection:()=>{Z(null),Le(null),Ut.current?.focus()}}),C.jsxs("div",{className:"topbar-tools",children:[C.jsxs("nav",{className:"header-navigation","aria-label":"Workspace navigation",children:[C.jsx("button",{type:"button",className:z?.cellId===null&&Rr?"active":"",title:"Library","aria-label":"Open Library","aria-expanded":z?.cellId===null&&Rr,disabled:G||g.state!=="ready"||!c,onClick:()=>os(),children:C.jsx($l,{size:17})}),aw.map(e=>{const t=e.icon;return C.jsx("button",{type:"button",className:b===e.id?"active":"",title:e.label,"aria-label":`Open ${e.label}`,"aria-current":b===e.id?"page":void 0,onClick:()=>Qt(e.id),children:C.jsx(t,{size:17})},e.id)})]}),C.jsx(Sf,{bookName:uo?.name??"",enabled:!!i,snapshot:Hr.snapshot,stale:Hr.stale,onRetry:Hr.retry},i)]})]}),!_t&&C.jsx("div",{className:"offline-banner",role:"status",children:"Offline · local import, search, editing, playback, history, and export remain available"}),C.jsxs(C.Fragment,{children:[b==="notebook"&&C.jsx(C.Fragment,{children:C.jsx("section",{className:"canvas",style:Ic,children:c?C.jsx("div",{className:"notebook-horizontal-scroll","data-composer-focus":"return",ref:Ut,tabIndex:0,"aria-label":"Notebook canvas",onKeyDown:jd,children:C.jsx("div",{className:"notebook-flow-frame",style:Hc,children:C.jsx(xf.Provider,{value:ws,children:C.jsx(Ef.Provider,{value:ju,children:C.jsx(Af.Provider,{value:on,children:C.jsx(_f.Provider,{value:nf,children:C.jsx(Rf.Provider,{value:Me,children:C.jsx(Pf.Provider,{value:lc,children:C.jsx(Mf.Provider,{value:Vc,children:C.jsx(Tf.Provider,{value:Ia,children:C.jsx(jf.Provider,{value:re,children:C.jsx($f.Provider,{value:Lc,children:C.jsxs(kf,{className:"notebook-flow",nodes:Uc,edges:Wc,nodeTypes:gw,edgeTypes:kw,viewport:Bc,onInit:e=>{Oo.current=e},onNodesChange:e=>{const t=e.filter(o=>o.type==="select");if(t.length>0){const o=new Set(lt.current);for(const l of t)l.selected?o.add(l.id):o.delete(l.id);wo(o);const n=[...o].at(-1)??null,r=Me&&o.has(Me)?Me:n;qo(r),Yo(r);const s=n?c?.cells.find(l=>l.id===n):void 0,a=n?ze.find(l=>l.id===n):void 0;s?Ae(s.slot):a&&Ae(a.data.slot)}ht(o=>{let n=ji(e,o);for(const r of e)r.type!=="position"||!r.dragging||!r.position||(n=Op(n,r.id,Ms(r.position)));return n})},onEdgesChange:e=>{$n(o=>wf(e,o));const t=e.filter(o=>o.type==="remove").map(o=>o.id);t.length>0&&Fd(t)},onNodeClick:(e,t)=>{const o=lt.current,n=o.has(t.id)?t.id:[...o].at(-1)??null;qo(n),Yo(n),n===t.id&&Ae(t.data.slot),Le(null),t.type!=="timeline"&&ro("selection")&&me(!0),t.type!=="timeline"&&o.size===1&&n===t.id&&!e.shiftKey&&!e.metaKey&&!e.ctrlKey&&(io(t.id),z?.cellId!==t.id&&Eo(t.id))},onPaneClick:()=>{ho(),Z(null),Le(null)},onPaneContextMenu:e=>{if(Qn.length===0)return;const t=hi(e.clientX,e.clientY);t&&(e.preventDefault(),Oc(t,{x:e.clientX,y:e.clientY},document.activeElement instanceof HTMLElement?document.activeElement:null))},onNodeDrag:(e,t)=>{ho(),Gt(Ms(t.position))},onNodeDragStop:(e,t,o)=>{const n=ji(o.map(({id:a})=>({id:a,type:"position",dragging:!1})),ze),r=Fp(n,t.id,o.map(a=>a.id),Ms(t.position)),s=Dp(ze,r);if(ht(r),Gt(null),s.length>0){const a=s.find(l=>l.id===t.id)??s[0];a&&Ae(a.data.slot),$d(s)}},isValidConnection:e=>c?ll(c.edges,e,c.cells):!1,onConnect:e=>{Ld(e)},onDrop:Tu,onDragLeave:Pu,onDragOver:Mu,minZoom:je,maxZoom:je,defaultEdgeOptions:ww,elementsSelectable:!0,multiSelectionKeyCode:hw,panOnDrag:vw,panOnScroll:!1,selectionKeyCode:null,selectionMode:bf.Partial,selectionOnDrag:!0,selectNodesOnDrag:!1,zoomOnScroll:!1,zoomOnPinch:!1,zoomActivationKeyCode:null,zoomOnDoubleClick:!1,preventScrolling:!1,deleteKeyCode:null,proOptions:bw,children:[C.jsx(Ff,{sections:zc,metrics:Tt,occupiedSlots:vt,previewSlot:Lo,mediaDropActive:ia&&!G,mediaDropSlot:wc,reviewRoles:Gr}),ze.length===0&&C.jsx(Df,{busy:G||g.state!=="ready",compact:Ki(je)>1.8,dimmed:ia||Lo!==null,onUpload:(e,t)=>{ts(e,t)},onPick:(e,t)=>{es(e,Lp(t))},onDownload:su,onBrowseLibrary:os})]})})})})})})})})})})})})}):C.jsxs("div",{className:"canvas-empty-state",children:[C.jsx("strong",{children:"No notebook available"}),C.jsx("button",{type:"button",onClick:()=>{_d(i)},children:"Reload book"})]})})}),b==="jobs"&&C.jsx(ab,{bookName:uo?.name??null,jobs:Ve,plans:Ur,assets:H,cells:c?.cells??sw,now:tc,busy:G,onRefresh:()=>i&&void F(i,c?.id),onCancelJob:e=>{Ba(e)},onRetryJob:e=>{Hd(e)},onContinuePlan:e=>{const t=Ur.find(o=>o.planId===e);t&&Kd(t)},onRevisePlan:(e,t)=>{const o=Ur.find(n=>n.planId===e);o&&Bd(o,t)}}),b==="settings"&&C.jsx(Of,{call:g.state==="ready"?w:void 0,providers:cc,loading:fc,error:mc,refreshed:pc,storage:uc,bookId:i,bookName:uo?.name??null,connection:$o,busy:G||g.state!=="ready",onRefresh:ln,onSave:Jd,onConnect:()=>{ns()}})]}),Ye&&ee&&C.jsx(qi,{actions:He,address:W(ee.slot),cellType:Ps(ee.type),deleteDisabled:G||Sr.has(ee.id),menuId:Vf(ee.id),position:Ye.position,returnFocus:Ye.returnFocus,onAction:Zu,onClose:ho,onDelete:ef}),Ye&&_o&&Qn.length>0&&C.jsx(qi,{actions:Qn,address:W(_o),cellType:"EMPTY",menuId:pw(_o),menuLabel:`Slot actions for ${W(_o)}`,position:Ye.position,returnFocus:Ye.returnFocus,onAction:Ju,onClose:ho}),ve&&J&&C.jsx(m.Suspense,{fallback:C.jsx("div",{role:"status",children:"Loading music-video editor…"}),children:C.jsx(Ol,{assembly:et,rhythm:wt,onFrameUpdate:et.seek,onExport:()=>{ni(),ws.onExport()},sequence:J,assets:H,audioArtifactId:ve.audioArtifactId,setup:ve.setup,returnFocus:ve.returnFocus,onApplySetup:Qa,onClose:()=>{wt.stop(),ni()},onCommit:Ya,onPlanDraft:Za,onApplyDraft:ei,onCreateTrack:oi,onRefreshAssets:async()=>{if(!i)throw new Error("Load or create a book first.");await F(i,c?.id)},onRestore:ti,onReviewSetup:e=>Xa(ve.key,ve.audioArtifactId,e??J)},ve.key)}),it&&C.jsx(m.Suspense,{fallback:C.jsx("div",{role:"status",children:"Loading alive captions…"}),children:C.jsx(Kb,{asset:it.asset,state:it.state,returnFocus:it.returnFocus,onClose:nu,onSave:e=>ai(it.asset.artifactId,e),onRender:(e,t)=>ru(it.asset.artifactId,e,t),onReanalyze:()=>si(it.key,it.asset.artifactId,!0)},it.key)}),Qo&&Xo&&jn&&J&&C.jsx(m.Suspense,{fallback:C.jsx("div",{role:"status",children:"Opening timeline preview…"}),children:C.jsx(Ol,{sequence:J,assets:H,assembly:et,rhythm:wt,setup:{status:"timeline"},address:W(jn.slot),initialFrame:Xo.initialFrame,returnFocus:Xo.returnFocus,onFrameUpdate:et.seek,onExport:()=>{Ri(),ws.onExport()},onClose:Ri,onApplySetup:Qa,onCommit:Ya,onPlanDraft:Za,onApplyDraft:ei,onCreateTrack:oi,onRefreshAssets:async()=>{await F(i,c?.id)},onRestore:ti,onReviewSetup:async()=>{await wt.load()}},`${i}:${jn.id}`)}),Y&&C.jsx(lb,{asset:Y.asset,address:Y.address,initialMode:Y.mode,initialInstruction:Y.initialInstruction,onInstructionChange:e=>{sa.current.set(Y.bookId,e),Ot(`videobook.image-edit-instruction:${Y.bookId}`,e)},composerPortalRef:Ar,actionsOpen:!!Ro,subjectMap:Y.subjectMap,subjectMapLoading:Y.subjectMapLoading,returnFocus:Y.returnFocus,analysisUnavailableReason:Y.asset.type==="image"&&!Y.asset.objectHash?"This version is missing its immutable object hash. Refresh the book data and reopen it.":null,onAnalyzeSubjects:e=>Cd(Y,e),onCaptureFrame:Y.asset.type==="video"||Y.asset.type==="final"?e=>Id(Y,e):void 0,onEditingChange:_r,replacementCandidates:rf,imageEditModels:Jo.models,imageEditModelsLoading:Jo.loading,defaultImageEditModelId:Jo.defaultModelId,onEstimateImageEditCost:Fc,onEditSubjects:e=>Gn(Y,e),onSubmitEditInstruction:(e,t)=>Su(Y,e,t),onClose:Kt},Y.key),C.jsx("input",{ref:Hs,type:"file",multiple:!0,hidden:!0,"aria-label":"Import files from actions",onChange:Wd}),Ne&&C.jsx(Gf,{media:Ne.media,sequence:Ne.media?void 0:J??void 0,assets:H.flatMap(e=>e.mediaUrl?[{artifactId:e.artifactId,mediaUrl:e.mediaUrl}]:[]),opener:Ne.opener,initialFrame:Ne.initialFrame,composerPortalRef:rc,actionsOpen:!!(Ro||Ei),onClose:()=>{jo(null),gt(null),Vt(null)},onActions:()=>{Ce(void 0,Ne.media?{asset_id:Ne.media.assetId}:void 0)}}),qe?.actionId&&C.jsx(Uf,{actions:Et,context:{...fn,entities:qe.resources?.entities,choices:{...fn.choices,...qe.resources?.choices}},initialActionId:qe.actionId,initialValues:qe.values,initialResult:qe.result,returnFocus:qe.opener,loading:br.loading,error:br.error,onClose:()=>{at.current+=1,Xe(null)},onBack:()=>{Ce(void 0,qe.values,qe.query,qe.opener)},onOpenAction:(e,t)=>{Ce(e,{...qe.values,...t})},onExecute:yu,onReview:Iu},qe.key),C.jsx(Wf,{chatTurns:fa,goalEvents:qc,previewTurnId:Ac,connected:g.state==="ready"&&_t,onBeginTurn:wi,onCommandRowHeightChange:vc,onHeightChange:yc,hidden:!ks,dockOpen:Rr,onDockOpenChange:me,contextualContent:pf,contextualHasHeader:mf,goalStatus:mo?C.jsx(fb,{goal:mo,disabled:g.state!=="ready",onOpen:()=>Zr(mo.cellId)}):null,commands:df,references:Vr,actions:Et,actionContext:fn,actionDiscovery:sf,actionStatus:br,actionsDisabled:G||g.state!=="ready",onOpenActions:()=>{Ce()},onCloseActionSearch:e=>{gt(null),!e&&Ai&&qa()},onDismissComposer:Ai?qa:void 0,bookId:i,callTool:w,chatModels:vr.models,disabled:G||aa||!i||g.state!=="ready",modelSelectionDisabled:!i||g.state!=="ready",connectionLabel:aa?"Removing selected subjects…":g.state==="ready"?"Load a book to begin":"Connecting to MCP…",mcpCalls:Rc,mcpFlash:Pc,onToggleMcpCall:Dc,selectedModel:Bs,inputSession:Yn,portalTarget:Ne&&(Ro||Ei)?nc:Y&&Ro?bc:null,pendingInput:he?"/apply":E?.kind==="generation"||E?.kind==="transcribe"?"/apply ":ue||E?"/apply":void 0,replacePendingInput:E?.kind==="transcribe",notice:Ht?{message:Ht.text,tone:Ht.tone}:null,outcomeSlot:_i?"sheet":"composer",onEnsureCatalog:Ed,onDismissNotice:()=>Do(null),onDismissPanel:he||ue||E?Fe:void 0,onExecute:ms,voiceCatalog:Hn,voice:Zt,onStartVoice:()=>{Z(null),ho(),Vt(null),Le(null),kt(null)},onModelChange:Ad,onSuccessfulExecute:cf,children:_i})]})}const Iw=await Kk().catch(()=>null);gf.createRoot(document.getElementById("root")).render(C.jsx(yw,{initialWorkspace:Iw}));
|