@three-blocks/devtools 1.0.0-alpha.193.g4eb273dec3a7 → 1.0.0-alpha.208.g664cb7c258f9

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.
@@ -1,2 +1,2 @@
1
1
  #!/usr/bin/env node
2
- import {e as e$1}from'./chunk-G65XQ3DF.js';import'./chunk-QMP2MC4S.js';import'./chunk-NE7SC2BX.js';import'./chunk-ZT6T2W4B.js';import {e}from'./chunk-NEWSG5RX.js';import'./chunk-ZDNZCQUQ.js';import'./chunk-5L2VS3BN.js';import {a}from'./chunk-HOZDD6PW.js';import {watch}from'fs';import v from'path';var o=class{static{a(this,"ShaderWatchQueue");}#s;#r;#a;#e;#t;#i=false;#n=false;constructor(r){if(this.#s=r.capture,this.#r=r.debounceMs??200,this.#a=r.onError??(()=>{}),!Number.isSafeInteger(this.#r)||this.#r<0||this.#r>6e4)throw new Error("Shader watch debounce must be an integer in 0...60000ms.")}notify(){this.#n||(this.#i=true,!this.#t&&(this.#e&&clearTimeout(this.#e),this.#e=setTimeout(()=>{this.#e=void 0,this.#o();},this.#r)));}#o(){this.#n||this.#t||!this.#i||(this.#i=false,this.#t=this.#s().catch(r=>{this.#a(r instanceof Error?r:new Error(String(r)));}).finally(()=>{this.#t=void 0,this.#i&&!this.#n&&this.notify();}));}async close(){this.#n=true,this.#i=false,this.#e&&clearTimeout(this.#e),this.#e=void 0,await this.#t;}};function y(e){let r=e.split(v.sep).join("/");return r===""||r.startsWith("node_modules/")||r.startsWith(".git/")||r.startsWith("dist/")||r===".three-blocks"||r.startsWith(".three-blocks/")}a(y,"ignored");async function W(e$2={}){let r=e$2.root??await e(e$2.start),d,l=new Promise(t=>{d=t;}),n=new o({...e$2.debounceMs!==void 0?{debounceMs:e$2.debounceMs}:{},...e$2.onError?{onError:e$2.onError}:{},capture:a(async()=>{let t=await e$1({root:r,...e$2.config?{config:e$2.config}:{},...e$2.driver?{driver:e$2.driver}:{},...e$2.driverKind?{driverKind:e$2.driverKind}:{},...e$2.serve?{serve:e$2.serve}:{},...e$2.url?{url:e$2.url}:{},...e$2.headed!==void 0?{headed:e$2.headed}:{},...e$2.attempts!==void 0?{attempts:e$2.attempts}:{}});e$2.onResult?.(t);},"capture")}),s,u=false,a$1=a(async()=>{u||(u=true,s?.close(),await n.close(),d?.());},"close");return s=watch(r,{recursive:true},(t,f)=>{y(f??"")||n.notify();}),s.on("error",t=>e$2.onError?.(t)),e$2.signal&&(e$2.signal.aborted?await a$1():e$2.signal.addEventListener("abort",()=>{a$1();},{once:true})),e$2.initial!==false&&n.notify(),{root:r,done:l,close:a$1}}a(W,"watchShaders");export{o as ShaderWatchQueue,W as watchShaders};
2
+ import {e as e$1}from'./chunk-5RSAQ74G.js';import'./chunk-HLYATKSG.js';import'./chunk-NE7SC2BX.js';import'./chunk-ZT6T2W4B.js';import {e}from'./chunk-NEWSG5RX.js';import'./chunk-ZDNZCQUQ.js';import'./chunk-5L2VS3BN.js';import {a}from'./chunk-HOZDD6PW.js';import {watch}from'fs';import v from'path';var o=class{static{a(this,"ShaderWatchQueue");}#s;#r;#a;#e;#t;#i=false;#n=false;constructor(r){if(this.#s=r.capture,this.#r=r.debounceMs??200,this.#a=r.onError??(()=>{}),!Number.isSafeInteger(this.#r)||this.#r<0||this.#r>6e4)throw new Error("Shader watch debounce must be an integer in 0...60000ms.")}notify(){this.#n||(this.#i=true,!this.#t&&(this.#e&&clearTimeout(this.#e),this.#e=setTimeout(()=>{this.#e=void 0,this.#o();},this.#r)));}#o(){this.#n||this.#t||!this.#i||(this.#i=false,this.#t=this.#s().catch(r=>{this.#a(r instanceof Error?r:new Error(String(r)));}).finally(()=>{this.#t=void 0,this.#i&&!this.#n&&this.notify();}));}async close(){this.#n=true,this.#i=false,this.#e&&clearTimeout(this.#e),this.#e=void 0,await this.#t;}};function y(e){let r=e.split(v.sep).join("/");return r===""||r.startsWith("node_modules/")||r.startsWith(".git/")||r.startsWith("dist/")||r===".three-blocks"||r.startsWith(".three-blocks/")}a(y,"ignored");async function W(e$2={}){let r=e$2.root??await e(e$2.start),d,l=new Promise(t=>{d=t;}),n=new o({...e$2.debounceMs!==void 0?{debounceMs:e$2.debounceMs}:{},...e$2.onError?{onError:e$2.onError}:{},capture:a(async()=>{let t=await e$1({root:r,...e$2.config?{config:e$2.config}:{},...e$2.driver?{driver:e$2.driver}:{},...e$2.driverKind?{driverKind:e$2.driverKind}:{},...e$2.serve?{serve:e$2.serve}:{},...e$2.url?{url:e$2.url}:{},...e$2.headed!==void 0?{headed:e$2.headed}:{},...e$2.attempts!==void 0?{attempts:e$2.attempts}:{}});e$2.onResult?.(t);},"capture")}),s,u=false,a$1=a(async()=>{u||(u=true,s?.close(),await n.close(),d?.());},"close");return s=watch(r,{recursive:true},(t,f)=>{y(f??"")||n.notify();}),s.on("error",t=>e$2.onError?.(t)),e$2.signal&&(e$2.signal.aborted?await a$1():e$2.signal.addEventListener("abort",()=>{a$1();},{once:true})),e$2.initial!==false&&n.notify(),{root:r,done:l,close:a$1}}a(W,"watchShaders");export{o as ShaderWatchQueue,W as watchShaders};
@@ -1,2 +1,2 @@
1
1
  #!/usr/bin/env node
2
- export{e as captureShaders,d as inspectShaderMatrix,f as testShaders}from'./chunk-G65XQ3DF.js';import'./chunk-QMP2MC4S.js';import'./chunk-NE7SC2BX.js';import'./chunk-ZT6T2W4B.js';import'./chunk-NEWSG5RX.js';import'./chunk-ZDNZCQUQ.js';import'./chunk-5L2VS3BN.js';import'./chunk-HOZDD6PW.js';
2
+ export{e as captureShaders,d as inspectShaderMatrix,f as testShaders}from'./chunk-5RSAQ74G.js';import'./chunk-HLYATKSG.js';import'./chunk-NE7SC2BX.js';import'./chunk-ZT6T2W4B.js';import'./chunk-NEWSG5RX.js';import'./chunk-ZDNZCQUQ.js';import'./chunk-5L2VS3BN.js';import'./chunk-HOZDD6PW.js';
@@ -1,2 +1,2 @@
1
1
  #!/usr/bin/env node
2
- export{b as RUNTIME_STATUS_RECEIPT_MAX_BYTES,a as RUNTIME_STATUS_RECEIPT_PATH,c as RUNTIME_STATUS_RECOVERY,e as findProjectRoot,i as formatShaderMatrixStatus,j as formatStatus,k as formatThreeBlocksStatus,f as inspectProject,g as inspectThreeBlocksStatus,d as parseRuntimeStatusReceipt,h as threeBlocksStatusIsFresh}from'./chunk-FP3ZS4BD.js';import'./chunk-76WRV5MZ.js';import'./chunk-JMS5NTP7.js';export{c as readInstalledShaderRuntime,b as snapshotShaderInputs}from'./chunk-G65XQ3DF.js';import'./chunk-QMP2MC4S.js';import'./chunk-NE7SC2BX.js';import'./chunk-ZT6T2W4B.js';import'./chunk-NEWSG5RX.js';import'./chunk-ZDNZCQUQ.js';import'./chunk-5L2VS3BN.js';import'./chunk-HOZDD6PW.js';
2
+ export{b as RUNTIME_STATUS_RECEIPT_MAX_BYTES,a as RUNTIME_STATUS_RECEIPT_PATH,c as RUNTIME_STATUS_RECOVERY,e as findProjectRoot,i as formatShaderMatrixStatus,j as formatStatus,k as formatThreeBlocksStatus,f as inspectProject,g as inspectThreeBlocksStatus,d as parseRuntimeStatusReceipt,h as threeBlocksStatusIsFresh}from'./chunk-KLGY4Q2M.js';import'./chunk-76WRV5MZ.js';import'./chunk-JMS5NTP7.js';export{c as readInstalledShaderRuntime,b as snapshotShaderInputs}from'./chunk-5RSAQ74G.js';import'./chunk-HLYATKSG.js';import'./chunk-NE7SC2BX.js';import'./chunk-ZT6T2W4B.js';import'./chunk-NEWSG5RX.js';import'./chunk-ZDNZCQUQ.js';import'./chunk-5L2VS3BN.js';import'./chunk-HOZDD6PW.js';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@three-blocks/devtools",
3
- "version": "1.0.0-alpha.193.g4eb273dec3a7",
3
+ "version": "1.0.0-alpha.208.g664cb7c258f9",
4
4
  "description": "Three Blocks devtools command engine for npx three-blocks; the runtime lives in three-blocks/devtools and the Vite plugin",
5
5
  "keywords": [
6
6
  "three",
@@ -79,7 +79,7 @@
79
79
  "@types/three": "0.185.0",
80
80
  "create-vite": "9.1.1",
81
81
  "playwright": "^1.61.1",
82
- "three-blocks": "0.2.0-alpha.193.g4eb273dec3a7",
82
+ "three-blocks": "0.2.0-alpha.208.g664cb7c258f9",
83
83
  "tsup": "^8.0.0",
84
84
  "typescript": "^5.9.3",
85
85
  "vite": "^7.2.2",
@@ -91,7 +91,7 @@
91
91
  "peerDependencies": {
92
92
  "playwright": "^1.61.1",
93
93
  "three": ">=0.185.0 <0.186.0",
94
- "three-blocks": "0.2.0-alpha.193.g4eb273dec3a7",
94
+ "three-blocks": "0.2.0-alpha.208.g664cb7c258f9",
95
95
  "typescript": ">=5.9.3 <7.0.0",
96
96
  "vite": ">=7.2.2 <9.0.0"
97
97
  },
@@ -1,76 +0,0 @@
1
- import {d,a as a$1,T as T$1,v,U,x as x$1,Q,m,l,h,g,O as O$1}from'./chunk-RQEPJ6GC.js';import {a}from'./chunk-EI7MMDWY.js';import b from'process';import {createServer}from'http';import {createRequire}from'module';import {mkdtemp,rm,lstat,realpath}from'fs/promises';import T from'path';import {tmpdir}from'os';import {pathToFileURL}from'url';var ve=Object.freeze([{id:"three-inspector-invalid-json",pattern:/is not valid JSON/iu},{id:"chromium-webgpu-experimental",pattern:/WebGPU is experimental/iu}]);function We(r){return ve.some(e=>e.pattern.test(r))}a(We,"isDocumentedBrowserNoise");function Z(r=b.env,e=b.platform){let t=r.THREE_BLOCKS_WEBGPU_BROWSER_ARGS?.split(/\s+/u).filter(Boolean);if(t&&t.length>0)return t;let n=["--enable-unsafe-webgpu"];return e==="darwin"&&n.push("--enable-gpu","--use-angle=metal"),e==="linux"&&n.push("--enable-features=Vulkan","--disable-vulkan-surface","--ignore-gpu-blocklist","--disable-gpu-driver-bug-workarounds","--disable-gpu-watchdog"),n}a(Z,"webgpuBrowserArgs");function ee(r=false,e=b.env){return r!==true&&e.THREE_BLOCKS_SOFTWARE_WEBGPU!=="1"}a(ee,"webgpuBrowserHeadless");var te="three-blocks.shader-capture.runtime.v1";var ce="/__three-blocks/shaders/capture",D="/__three-blocks/shaders/telemetry",le="/__three-blocks/shaders/runtime.js",ue="/__three-blocks/shaders/bootstrap.js",he="/__three-blocks/shaders/bridge.js",me=d.manifest*2,K=/^[a-z0-9][a-z0-9_-]{0,63}$/u,fe=64,pe=2e3,Be=[/is not valid JSON/iu,/WebGPU is experimental/iu];async function xe(){try{return (await import('playwright')).chromium}catch(r){throw new Error('Shader browser work requires the optional "playwright" package. Install it in the project and run `npx playwright install chromium`.',{cause:r})}}a(xe,"loadChromium");async function Oe(r){let e;try{e=createRequire(T.join(r,"package.json")).resolve("vite");}catch(n){throw new Error("Shader capture requires Vite in the target project.",{cause:n})}let t=await import(pathToFileURL(e).href);if(typeof t.createServer!="function")throw new Error(`The target project's Vite entry does not export createServer(): ${e}`);return t.createServer}a(Oe,"loadProjectCreateServer");var W=class{static{a(this,"CaptureInbox");}#e=new Map;#t=new Map;wait(e,t){let n=this.#t.get(e);if(n!==void 0)return this.#t.delete(e),Promise.resolve(n);if(this.#e.has(e))throw new Error(`A shader capture is already waiting for scene "${e}".`);return new Promise((a,o)=>{let i=setTimeout(()=>{this.#e.delete(e),o(new Error(`Shader capture "${e}" timed out after ${t}ms.`));},t);this.#e.set(e,{resolve:a,reject:o,timer:i});})}receive(e){if(!a$1(e)||typeof e.scene!="string"||!K.test(e.scene))throw new Error("Capture POST has no safe scene key.");if(!this.#t.has(e.scene)&&!this.#e.has(e.scene)&&this.#t.size>=fe)throw new Error("Capture POST exceeds the scene inbox limit.");let t=this.#e.get(e.scene);t?(clearTimeout(t.timer),this.#e.delete(e.scene),t.resolve(e)):this.#t.set(e.scene,e);}cancel(e,t){let n=this.#e.get(e);n&&(clearTimeout(n.timer),this.#e.delete(e),n.reject(t));}rejectAll(e){for(let t of this.#e.values())clearTimeout(t.timer),t.reject(e);this.#e.clear(),this.#t.clear();}};async function je(r,e){let t=await Promise.race([e.then(n=>({kind:"capture",value:n})),r.then(()=>({kind:"navigation"}))]);return t.kind==="capture"?t.value:e}a(je,"waitForShaderCaptureAcrossNavigation");var q=class{static{a(this,"TelemetryHub");}#e=new Map;#t=new Map;markFirstRequest(e){K.test(e)&&!this.#t.has(e)&&this.#t.set(e,Date.now());}firstRequest(e){return this.#t.get(e)}receive(e){if(!a$1(e)||typeof e.scene!="string"||!K.test(e.scene))throw new Error("Shader telemetry has no bounded scene key.");if(!this.#e.has(e.scene)&&this.#e.size>=fe)throw new Error("Shader telemetry exceeds the scene limit.");this.#e.set(e.scene,e);}read(e){return this.#e.get(e)}clear(e){this.#e.delete(e),this.#t.delete(e);}},Me=a(async(r,e,t,n,a)=>{let o=0;for(;r.__threeBlocksParityUsesAnimationLoop!==true&&o<e;)await n(),o+=1;if(r.__threeBlocksParityUsesAnimationLoop===true){let i=Number(r.__threeBlocksParityCompletedFrame||0),s=Number(t),l=Number.isSafeInteger(s)&&s>=i?s:i+e;for(r.__threeBlocksParityTargetFrame=l;Number(r.__threeBlocksParityCompletedFrame||0)<l;)await n();}return await a(),Number(r.__threeBlocksParityCompletedFrame||0)},"settleShaderParityFrames");function G(r){return `(() => {
2
- const root = globalThis;
3
- const scene = new URL(location.href).searchParams.get('captureId')
4
- || 'default';
5
- const randomSeed = (value) => {
6
- let state = 2166136261;
7
- for (let index = 0; index < value.length; index++) state = Math.imul(state ^ value.charCodeAt(index), 16777619) >>> 0;
8
- return state === 0 ? 0x9e3779b9 : state;
9
- };
10
- const advanceRandom = (state) => {
11
- state ^= state << 13;
12
- state ^= state >>> 17;
13
- state ^= state << 5;
14
- return state >>> 0;
15
- };
16
- const parityMode = new URL(location.href).searchParams.get('threeBlocksShaderMode');
17
- if (parityMode === 'live' || parityMode === 'precompiled') {
18
- root.__threeBlocksParityEpoch = 1700000000000;
19
- root.__threeBlocksParityTime = 0;
20
- Date.now = () => root.__threeBlocksParityEpoch + Number(root.__threeBlocksParityTime || 0);
21
- }
22
- const randomStreams = new Map();
23
- Math.random = () => {
24
- const stackLine = String(new Error().stack || '').split('\\n')[2] || 'unknown';
25
- const originIndex = stackLine.indexOf(location.origin);
26
- const callsite = (originIndex >= 0 ? stackLine.slice(0, originIndex) : stackLine).trim() || 'anonymous';
27
- const next = advanceRandom(randomStreams.get(callsite) ?? randomSeed(scene + '|' + callsite));
28
- randomStreams.set(callsite, next);
29
- return next / 4294967296;
30
- };
31
- const readiness = { workerReady: false, assetsReady: false, textReady: false, compileEnd: false, firstFrame: false };
32
- const stats = { buildCalls: 0, renderBuilds: 0, computeBuilds: 0, registeredBuilds: 0, registeredRenderBuilds: 0, registeredComputeBuilds: 0, buildMs: 0, syncBuildMs: 0, asyncBuildElapsedMs: 0, precompiledSetupMs: 0, maxSyncBuildMs: 0, maxPrecompiledSetupMs: 0, hydrationMs: 0, maxHydrationMs: 0, injected: 0, injectedRender: 0, injectedCompute: 0, missed: 0, missedRender: 0, missedCompute: 0, missedKeys: [] };
33
- const settleParityFrames = ${Me.toString()};
34
- const settle = (frames, requestedTarget) => settleParityFrames(
35
- root,
36
- frames,
37
- requestedTarget,
38
- () => new Promise((resolve) => requestAnimationFrame(resolve)),
39
- () => new Promise((resolve) => setTimeout(resolve, 100)),
40
- );
41
- const bridge = { protocolVersion: 1, compatibility: ${JSON.stringify(r)}, transform: ${x$1}, readiness, stats, settle };
42
- root.__threeBlocksShaderTools = bridge;
43
- requestAnimationFrame(() => requestAnimationFrame(() => { readiness.firstFrame = true; }));
44
- const poll = async () => {
45
- try {
46
- const response = await fetch('/__three-blocks/shaders/telemetry?scene=' + encodeURIComponent(scene), { cache: 'no-store' });
47
- if (response.status !== 204 && response.ok) {
48
- const payload = await response.json();
49
- if (payload.protocolVersion !== 1 || payload.compatibility !== bridge.compatibility || payload.transform !== bridge.transform) throw new Error('incompatible shader telemetry');
50
- Object.assign(stats, payload.stats);
51
- readiness.workerReady = true;
52
- if (payload.settled === true) {
53
- readiness.assetsReady = true;
54
- readiness.textReady = true;
55
- readiness.compileEnd = true;
56
- }
57
- const smoke = root.__threeBlocksSmoke && typeof root.__threeBlocksSmoke === 'object' ? root.__threeBlocksSmoke : { protocolVersion: 1, worker: { offscreenCanvas: true, visible: true }, readiness: {} };
58
- smoke.readiness = { ...(smoke.readiness || {}), ...readiness };
59
- root.__threeBlocksSmoke = smoke;
60
- }
61
- } catch {}
62
- setTimeout(poll, 40);
63
- };
64
- void poll();
65
- })();`}a(G,"publicBridgeScript");function we(r,e,t,n,a=false){let o=new URL(r.url??"/","http://three-blocks.invalid"),i=o.pathname;if(a&&r.method==="GET"&&/^\/three-blocks\/shaders\/[a-z0-9][a-z0-9_-]{0,63}\.json$/u.test(i))return e.statusCode=204,e.end(),true;if(i===D&&r.method==="GET"){let m=o.searchParams.get("scene")??"",u=n.read(m);return u===void 0?(e.statusCode=204,e.end()):(e.statusCode=200,e.setHeader("Content-Type","application/json"),e.end(JSON.stringify(u))),true}let s=i===ce,l=i===D;if(!s&&!l)return false;if(r.method!=="POST")return e.statusCode=405,e.end("POST required"),true;let h=[],p=0,y=false;return r.on("data",m=>{p+=m.byteLength,p>me?y=true:h.push(m);}),r.on("end",()=>{if(y){e.statusCode=413,e.end("capture payload too large");return}try{let m=JSON.parse(Buffer.concat(h).toString("utf8"));l?n.receive(m):t.receive(m),e.statusCode=204,e.end();}catch(m){e.statusCode=400,e.end(m instanceof Error?m.message:String(m));}}),true}a(we,"handleCaptureEndpoint");function Fe(r,e,t,n){return {name:"three-blocks:shader-capture-endpoint",transformIndexHtml(){return [{tag:"script",children:G(n),injectTo:"head-prepend"}]},configureServer(a){a.middlewares.use((o,i,s)=>{let h=new URL(o.url??"/","http://three-blocks.invalid").searchParams.get("captureId");h!==null&&e.markFirstRequest(h),!we(o,i,r,e,t)&&s();});}}}a(Fe,"captureEndpointPlugin");function ne(r,e,t){let n=new URL(e.url,r);for(let[a,o]of Object.entries(t))n.searchParams.set(a,o);return n.href}a(ne,"browserUrl");function Le(r,e){let t=new URL(e.url,r);for(let n of ["capture","precompiled"])t.searchParams.delete(n);return t.searchParams.set("captureId",e.key),t.searchParams.set("threeBlocksShaderMode","precompiled"),t.searchParams.set("tbStats","1"),t.href}a(Le,"publishedBrowserUrl");function ae(r){return Be.some(e=>e.test(r))}a(ae,"knownNoise");async function C(r){let e;try{await Promise.race([r(),new Promise(t=>{e=setTimeout(t,pe);})]);}catch{}finally{e&&clearTimeout(e);}}a(C,"closeBrowserResource");async function oe(r){let e;try{return await Promise.race([r().catch(()=>null),new Promise(t=>{e=setTimeout(()=>t(null),pe);})])}finally{e!==void 0&&clearTimeout(e);}}a(oe,"readPageDiagnostic");function H(r){let e=a(()=>{},"resolveFirst"),t=new Promise(i=>{e=i;}),n={console:[],page:[],first:t},a$1=false,o=a(i=>{a$1||(a$1=true,e(new Error(i)));},"report");return r.on("console",i=>{let s=i.type()==="warning"&&/\[three-blocks\/shaders\].*(?:has no entry|manifest miss|hydration)/iu.test(i.text());if(i.type()!=="error"&&!s||ae(i.text()))return;let l=i.location().url,h=l.length>0?`${i.text()} (${l})`:i.text();n.console.push(h),o(`Browser console ${s?"warning":"error"}: ${h}`);}),r.on("pageerror",i=>{if(ae(i.message))return;let s=i.stack||i.message;n.page.push(s),o(`Browser page error: ${s}`);}),r.on("crash",()=>o("Browser page crashed before shader capture completed.")),r.on("close",()=>o("Browser page closed before shader capture completed.")),n}a(H,"collectErrors");function B(r,e,t=false){return typeof r[e]=="boolean"?r[e]:t}a(B,"booleanField");function Ae(r){if(!a$1(r))throw new Error("Browser shader stats are unavailable.");let e=a((t,n=true)=>{let a=r[t];if(typeof a!="number"||!Number.isFinite(a)||a<0||n&&!Number.isSafeInteger(a))throw new Error(`Browser shader stats.${t} is invalid.`);return a},"read");return {buildCalls:e("buildCalls"),renderBuilds:e("renderBuilds"),computeBuilds:e("computeBuilds"),registeredBuilds:e("registeredBuilds"),registeredRenderBuilds:e("registeredRenderBuilds"),registeredComputeBuilds:e("registeredComputeBuilds"),buildMs:e("buildMs",false),syncBuildMs:e("syncBuildMs",false),asyncBuildElapsedMs:e("asyncBuildElapsedMs",false),precompiledSetupMs:e("precompiledSetupMs",false),maxSyncBuildMs:e("maxSyncBuildMs",false),maxPrecompiledSetupMs:e("maxPrecompiledSetupMs",false),hydrationMs:e("hydrationMs",false),maxHydrationMs:e("maxHydrationMs",false),injected:e("injected"),injectedRender:e("injectedRender"),injectedCompute:e("injectedCompute"),missed:e("missed"),missedRender:e("missedRender"),missedCompute:e("missedCompute"),...Array.isArray(r.missedKeys)&&r.missedKeys.every(t=>typeof t=="string")?{missedKeys:r.missedKeys}:{}}}a(Ae,"parseStats");function L(r,e,t,n,a){if(!a$1(r))throw new Error("The page did not expose the public shader devtools bridge.");if(!t&&r.protocolVersion!==1)throw new Error(`Scene "${e.key}" exposed an unsupported shader bridge protocol.`);let o=r.readiness;if(!a$1(o))throw new Error("The shader bridge readiness snapshot is invalid.");let i={workerReady:B(o,"workerReady"),assetsReady:B(o,"assetsReady"),textReady:e.requiresText?B(o,"textReady"):true,compileEnd:B(o,"compileEnd"),firstFrame:B(o,"firstFrame",t)};if(!i.workerReady||!i.assetsReady||!i.textReady||!i.compileEnd)throw new Error(`Scene "${e.key}" did not reach worker/assets/text/compile readiness.`);let s=t?a:r.compatibility,l=t?x$1:r.transform;if(s!==a||l!==x$1)throw new Error(`Scene "${e.key}" exposed incompatible shader bridge metadata.`);return U(n),{compatibility:a,transform:l,readiness:i,stats:Ae(r.stats)}}a(L,"parseBridge");async function A(r,e){return r.evaluate(t=>{let n=globalThis;if(!t)return n.__threeBlocksShaderTools??null;let a=n.__threeBlocks,o=n.__threeBlocksTslStats;if(!a||typeof a!="object")return null;let i=a;return {readiness:{workerReady:i.workerReady===true,assetsReady:i.loadEnd===true||i.assetsReady===true,textReady:i.textReady===true,compileEnd:i.compileEnd===true,firstFrame:true},stats:o}},e)}a(A,"readBridge");async function x(r,e,t,n){return r.evaluate(async a$1=>{let i=globalThis.__threeBlocksShaderTools;if(i&&typeof i=="object"){let h=Reflect.get(i,"settle");if(typeof h=="function"){let p=await h(a$1.frames,a$1.targetFrame);return typeof p=="number"&&Number.isSafeInteger(p)?p:0}}if(!a$1.legacy||!a$1.modulePath)throw new Error("The public shader bridge does not provide deterministic settle().");let s=await import(a$1.modulePath);if(!s.store||typeof s.store!="object")throw new Error("Legacy deterministic store is unavailable.");let l=s.store;return l.recordFrameCount=0,l.recordFrameRate=60,l.recordTotalFrames=a$1.frames,l.recording=true,await new Promise((h,p)=>{let y=Date.now(),m=a(()=>{if(l.recording===false)return h();if(Date.now()-y>a$1.timeoutMs)return p(new Error("Legacy deterministic settle timed out."));setTimeout(m,25);},"poll");m();}),0},{frames:t,targetFrame:n,legacy:e.bridge.legacyLab,modulePath:e.bridge.deterministicModule??null,timeoutMs:e.timeoutMs})}a(x,"settlePage");async function ie(r,e,t){e.readiness.selector===void 0&&e.readiness.global===void 0||await Promise.race([r.waitForFunction(n=>{let a=globalThis;if(n.selector!==void 0&&a.document?.querySelector(n.selector)==null)return false;if(n.global===void 0)return true;let o=a;for(let l of n.global.split(".")){if((typeof o!="object"||o===null)&&typeof o!="function")return false;o=Reflect.get(o,l);}if(o===true)return true;if(typeof o!="object"||o===null||typeof Reflect.get(o,"then")!="function")return false;let i=a.__threeBlocksReadinessState,s=i instanceof Map?i:new Map;return i instanceof Map||(a.__threeBlocksReadinessState=s),s.has(o)||(s.set(o,false),Promise.resolve(o).then(()=>s.set(o,true),()=>s.set(o,false))),s.get(o)===true},e.readiness,{timeout:e.timeoutMs}),t.first.then(n=>Promise.reject(n))]);}a(ie,"waitForConfiguredReadiness");async function se(r){let e=r.locator("canvas"),n=(await e.evaluateAll(a=>a.map((o,i)=>{let s=o.getBoundingClientRect();return {index:i,area:Math.max(0,s.width)*Math.max(0,s.height)}}))).sort((a,o)=>o.area-a.area)[0];if(n===void 0||n.area<=0)throw new Error("Published page has no visible renderer canvas.");return Buffer.from(await e.nth(n.index).screenshot({type:"png"}))}a(se,"primaryCanvasScreenshot");async function V(r,e,t,n,a,o){let i=ye(n,a),s=await Q(),l=`(() => {
66
- const runtime = globalThis[Symbol.for(${JSON.stringify(te)})];
67
- if (!runtime || typeof runtime.configureThreeBlocksShaderCapture !== 'function') {
68
- throw new Error('@three-blocks/devtools attached shader capture runtime is incompatible.');
69
- }
70
- runtime.configureThreeBlocksShaderCapture(${JSON.stringify(i).replaceAll("<","\\u003c")});
71
- })();`;await r.addInitScript({content:`${s}
72
- ${l}`}),await r.addInitScript({content:G(o)}),await r.route("**/*",async h=>{let p=h.request(),y=new URL(p.url()),m=y.pathname;if(p.method()==="GET"&&n!=="precompiled"&&/^\/three-blocks\/shaders\/[a-z0-9][a-z0-9_-]{0,63}\.json$/u.test(m)){await h.fulfill({status:204});return}if(m===D&&p.method()==="GET"){let f=t.read(y.searchParams.get("scene")??"");await h.fulfill(f===void 0?{status:204}:{status:200,contentType:"application/json",body:JSON.stringify(f)});return}let u=m===ce,c=m===D;if((u||c)&&p.method()==="POST"){let f=p.postDataBuffer()??Buffer.alloc(0);if(f.byteLength>me){await h.fulfill({status:413,body:"capture payload too large"});return}try{let w=JSON.parse(f.toString("utf8"));c?t.receive(w):e.receive(w),await h.fulfill({status:204});}catch(w){await h.fulfill({status:400,body:w instanceof Error?w.message:String(w)});}return}await h.continue();});}a(V,"configureAttachedContext");var De=Object.freeze({".avif":"image/avif",".css":"text/css; charset=utf-8",".gif":"image/gif",".html":"text/html; charset=utf-8",".ico":"image/x-icon",".jpeg":"image/jpeg",".jpg":"image/jpeg",".js":"text/javascript; charset=utf-8",".json":"application/json; charset=utf-8",".mjs":"text/javascript; charset=utf-8",".mp4":"video/mp4",".png":"image/png",".svg":"image/svg+xml",".wasm":"application/wasm",".webm":"video/webm",".webp":"image/webp",".woff":"font/woff",".woff2":"font/woff2"});function Ne(r){let e=[`<script src="${he}"></script>`,`<script type="module" src="${ue}"></script>`].join(""),t=/<head(?:\s[^>]*)?>/iu.exec(r);return t===null?`${e}${r}`:`${r.slice(0,t.index+t[0].length)}${e}${r.slice(t.index+t[0].length)}`}a(Ne,"injectStaticShaderCaptureHtml");function Ie(r,e){let t=ye(r,e);return [`import { configureThreeBlocksShaderCapture } from ${JSON.stringify(le)};`,`configureThreeBlocksShaderCapture( ${JSON.stringify(t).replaceAll("<","\\u003c")} );`].join(`
73
- `)}a(Ie,"staticCaptureBootstrap");function ye(r,e){return {capture:r==="capture",forceLive:r!=="precompiled",settleFrames:e.settleFrames,settleTimeoutMs:e.settleTimeoutMs??3e4,readiness:e.readiness,transform:x$1}}a(ye,"shaderCaptureConfiguration");async function Ue(r,e){let t=await m(r,e,i=>/\.(?:c|m)?js$/u.test(i),16384),n=false,a=false,o;for(let i of t){let s=(await l(r,i,d.texture,"Static application JavaScript")).data.toString("utf8");if(s.includes("nodeBuilderStateProvider")&&(n=true),s.includes("three-blocks.shader-capture.runtime.v1")&&(a=true,o??=i),n&&a)break}if(!n||!a)throw new Error("The static build does not contain the Three.js shader capture transform. Run `shaders capture` without an explicit driver or URL to preview adapter wiring and build automatically, or add the manual adapter from the package README and rebuild.");return {seen:true,applied:true,alreadyPresent:false,captureApplied:true,...o===void 0?{}:{id:o}}}a(Ue,"inspectStaticCaptureTransform");async function $e(r,e){let t;try{t=decodeURIComponent(e);}catch{return}if(t.includes("\0"))return;let n=t.replace(/^\/+/u,""),a=T.resolve(r,n.length===0?"index.html":n);if(!h(r,a)||a===r||(await g(a)&&(await lstat(a)).isDirectory()&&(a=T.join(a,"index.html")),!await g(a)&&T.extname(a).length===0&&(a=T.join(r,"index.html")),!await g(a)))return;let o=await l(r,a,d.texture,"Static application asset");return {data:o.data,file:o.path}}a($e,"staticRequestFile");async function He(r,e,t,n,a){let o=await realpath(r.root),i=await realpath(T.resolve(o,r.serve));if(!h(o,i)||i===o)throw new Error("--serve must name a built application directory inside the project root.");let s=await Ue(o,i),l=await O$1(),h$1=Ie(e,t),p=G(v(r.runtime.three)),y=createServer((u,c)=>{(async()=>{if(we(u,c,n,a,e!=="precompiled"))return;let f=new URL(u.url??"/","http://three-blocks.invalid");if(u.method!=="GET"&&u.method!=="HEAD"){c.statusCode=405,c.end("GET or HEAD required");return}let w=f.pathname===le?l:f.pathname===ue?h$1:f.pathname===he?p:void 0;if(w!==void 0){c.statusCode=200,c.setHeader("Content-Type","text/javascript; charset=utf-8"),c.setHeader("Cache-Control","no-store"),c.end(u.method==="HEAD"?void 0:w);return}let g=await $e(i,f.pathname);if(g===void 0){c.statusCode=404,c.end("Not found");return}let v=T.extname(g.file).toLowerCase(),R=v===".html"?Buffer.from(Ne(g.data.toString("utf8"))):g.data;c.statusCode=200,c.setHeader("Content-Type",De[v]??"application/octet-stream"),c.setHeader("Content-Length",String(R.byteLength)),c.setHeader("Cache-Control","no-store"),c.end(u.method==="HEAD"?void 0:R);})().catch(f=>{if(c.headersSent)return c.destroy(f instanceof Error?f:void 0);c.statusCode=500,c.end(f instanceof Error?f.message:String(f));});});await new Promise((u,c)=>{y.once("error",c),y.listen(0,"127.0.0.1",()=>{y.off("error",c),u();});});let m=y.address();if(!m||typeof m=="string")throw new Error("Static capture server did not expose an ephemeral TCP address.");return {server:y,baseUrl:`http://127.0.0.1:${m.port}`,transform:s}}a(He,"startStaticShaderServer");function Ve(r,e,t){return r===e?true:t&&r!==void 0&&r!=="capture"&&e!=="capture"}a(Ve,"canReuseShaderBrowserSession");function de(r){let e=r instanceof Error?r.message:String(r);return e.includes("Execution context was destroyed")&&e.includes("navigation")}a(de,"isRetryableShaderObservationNavigation");var O=class{static{a(this,"PlaywrightShaderDriver");}#e;#t=new W;#n=new q;#u;#h;#o;#i;#r;#a;#m;#d;#f;#c=0;#l;constructor(e){this.#e=e;}#s(){return this.#u?.status??this.#h??{seen:false,applied:false,alreadyPresent:false}}async#p(e){if(this.#r?.isConnected()===true)return;this.#r=void 0;let t=await xe();this.#l??=await mkdtemp(T.join(tmpdir(),"three-blocks-shader-cache-")),this.#r=await t.launch({headless:ee(this.#e.headed===true),args:[...Z(),`--disk-cache-dir=${this.#l}`],timeout:e.timeoutMs}),this.#c=0;}async#w(e,t){let n=this.#o!==void 0||this.#i!==void 0||this.#e.url!==void 0&&this.#a!==void 0,a=this.#i!==void 0?this.#d===e:Ve(this.#d,e,t.bridge.legacyLab);if(n&&a){this.#d=e,await this.#p(t);return}if(n&&await this.close(),this.#d=e,this.#e.url!==void 0){let o=new URL(this.#e.url);if(!["http:","https:"].includes(o.protocol)||o.username||o.password||o.hash)throw new Error("Attached shader URL must be an HTTP(S) URL without credentials or a fragment.");this.#a=o.href,this.#h={seen:true,applied:true,alreadyPresent:false,captureApplied:true,id:"attached-application"},await this.#p(t);return}if(this.#e.serve!==void 0)try{let o=await He({root:this.#e.root,runtime:this.#e.runtime,serve:this.#e.serve,...this.#e.headed===void 0?{}:{headed:this.#e.headed}},e,t,this.#t,this.#n);this.#i=o.server,this.#h=o.transform,this.#a=o.baseUrl,await this.#p(t);return}catch(o){throw await this.close(),o}this.#u=T$1(this.#e.runtime.three,{disableTimestampQueries:b.env.THREE_BLOCKS_SOFTWARE_WEBGPU==="1",...t.bridge.legacyLab?{}:{capture:{capture:e==="capture",forceLive:e!=="precompiled",settleFrames:t.settleFrames,settleTimeoutMs:t.settleTimeoutMs??3e4,readiness:t.readiness}}}),this.#m={THREE_BLOCKS_SHADER_TOOL:b.env.THREE_BLOCKS_SHADER_TOOL,THREE_BLOCKS_PRECOMPILE_CAPTURE_SERVER:b.env.THREE_BLOCKS_PRECOMPILE_CAPTURE_SERVER},b.env.THREE_BLOCKS_SHADER_TOOL="1",b.env.THREE_BLOCKS_PRECOMPILE_CAPTURE_SERVER="1";try{let o=await Oe(this.#e.root);this.#o=await o({root:this.#e.root,logLevel:"error",plugins:[this.#u.plugin,Fe(this.#t,this.#n,e!=="precompiled",v(this.#e.runtime.three))],server:{host:"127.0.0.1",port:0}}),await this.#o.listen();let i=this.#o.httpServer?.address();if(!i||typeof i=="string")throw new Error("Vite did not expose an ephemeral TCP address.");this.#a=`http://127.0.0.1:${i.port}`,await this.#p(t);}catch(o){throw await this.close(),o}}async capture(e,t){let n=Date.now();if(await this.#w("capture",t),!this.#r||!this.#a)throw new Error("Shader browser driver did not start.");let a$2=this.#r,o=await a$2.newContext({viewport:t.viewport});this.#e.url!==void 0&&await V(o,this.#t,this.#n,"capture",t,v(this.#e.runtime.three));let i=await o.newPage(),s=H(i);this.#n.clear(e.key);let l=this.#t.wait(e.key,t.timeoutMs),h=Promise.race([l,s.first.then(u=>Promise.reject(u))]),p=a(()=>{},"resolveDisconnected"),y=new Promise(u=>{p=u;}),m=a(()=>p(new Error("Shader capture browser disconnected before posting a manifest.")),"onDisconnected");a$2.on("disconnected",m);try{let u=i.goto(ne(this.#a,e,{threeBlocksShaderCapture:"1",capture:"1",captureId:e.key,captureFrames:String(Math.max(4,t.settleFrames)),settleFrames:String(t.settleFrames)}),{waitUntil:"domcontentloaded",timeout:t.timeoutMs}),c=await je(u,Promise.race([h,y.then(w=>Promise.reject(w))]));U(this.#s());let f=[...s.page,...s.console];if(f.length>0)throw new Error(`Capture browser errors:
74
- - ${f.join(`
75
- - `)}`);return a$1(c)?{...c,timing:{...a$1(c.timing)?c.timing:{},launch:n,...this.#n.firstRequest(e.key)===void 0?{}:{firstRequest:this.#n.firstRequest(e.key)},posted:Date.now()}}:c}catch(u){let c=u instanceof Error?u:new Error(String(u));this.#t.cancel(e.key,c),await l.catch(()=>{});let f=this.#n.read(e.key);if(c.message.includes("timed out")){let w=await oe(()=>i.evaluate(()=>{let g=globalThis,v=g.__threeBlocksShaderTools,R=v&&typeof v=="object"?v:void 0,ge=g.document,k=Reflect.get(g,Symbol.for("three-blocks.shader-capture.cache-value.v1")),j=g.location,Se=j!==null&&typeof j=="object"&&typeof Reflect.get(j,"href")=="string"?String(Reflect.get(j,"href")):"http://three-blocks.invalid/",be=new URL(Se).searchParams.get("captureId")??"default",J=k!==null&&typeof k=="object"&&typeof Reflect.get(k,"registrations")=="function"?Reflect.apply(Reflect.get(k,"registrations"),k,[be]):void 0;return {documentReadyState:ge?.readyState??null,parityTargetFrame:Number(g.__threeBlocksParityTargetFrame??0),parityCompletedFrame:Number(g.__threeBlocksParityCompletedFrame??0),readiness:R?.readiness??null,captureCache:k!==null&&typeof k=="object"?{activeScene:Reflect.get(k,"activeScene")??null,registrations:Array.isArray(J)?J.slice(0,16).map(E=>E!==null&&typeof E=="object"?{key:Reflect.get(E,"key")??null,kind:Reflect.get(E,"kind")??null}:null):null}:null,threeRuntimeResources:performance.getEntriesByType("resource").map(E=>E.name).filter(E=>E.includes("three.webgpu"))}}));throw new Error(`${c.message} Last capture state for "${e.key}": ${JSON.stringify({page:w,telemetry:f??null,transform:this.#s()})}`)}throw c}finally{a$2.off("disconnected",m),await C(()=>o.close()),this.#c++,(!a$2.isConnected()||this.#c>=(t.browserRelaunchScenes??8))&&(this.#r===a$2&&(this.#r=void 0),await C(()=>a$2.close()),this.#c=0);}}async observe(e,t,n,a){for(let o=0;o<2;o++)try{return await this.#y(e,t,n,a)}catch(i){if(o===0&&de(i))continue;throw i}throw new Error(`Shader observation retry was exhausted for scene "${e.key}".`)}async#y(e,t,n,a){if(await this.#w(t,n),!this.#r||!this.#a)throw new Error("Shader browser driver did not start.");let o=await this.#r.newContext({viewport:n.viewport});this.#e.url!==void 0&&await V(o,this.#t,this.#n,t,n,v(this.#e.runtime.three));let i=await o.newPage(),s=H(i);this.#n.clear(e.key);try{await i.goto(ne(this.#a,e,{threeBlocksShaderCapture:"1",threeBlocksShaderMode:t,captureId:e.key,...t==="live"?{precompiled:"0"}:{}}),{waitUntil:"domcontentloaded",timeout:n.timeoutMs}),await Promise.race([i.waitForFunction(n.bridge.legacyLab?"globalThis.__threeBlocks?.compileEnd === true":"globalThis.__threeBlocksShaderTools?.readiness?.compileEnd === true",void 0,{timeout:n.timeoutMs}),s.first.then(u=>Promise.reject(u))]),L(await A(i,n.bridge.legacyLab),e,n.bridge.legacyLab,this.#s(),v(this.#e.runtime.three)),await ie(i,n,s),await Promise.race([i.waitForFunction(n.bridge.legacyLab?"true":"globalThis.__threeBlocksShaderTools?.readiness?.firstFrame === true",void 0,{timeout:n.timeoutMs}),s.first.then(u=>Promise.reject(u))]),await x(i,n,1);let l=Buffer.from(await i.screenshot({type:"png"})),h=e.parityFrames??n.parity.frames,p=await x(i,n,h,a),y=Buffer.from(await i.screenshot({type:"png"}));e.parityFrames!==void 0&&h<n.parity.frames&&await x(i,n,n.parity.frames-h);let m=L(await A(i,n.bridge.legacyLab),e,n.bridge.legacyLab,this.#s(),v(this.#e.runtime.three));return this.#f===void 0&&(this.#f=await i.evaluate(async()=>{let u=Reflect.get(navigator,"gpu"),c=typeof u=="object"&&u!==null?Reflect.get(u,"requestAdapter"):void 0,f=typeof c=="function"?await Reflect.apply(c,u,[]):void 0,w=typeof f=="object"&&f!==null?Reflect.get(f,"info"):void 0,g=["description","device","architecture","vendor"].flatMap(v=>{let R=typeof w=="object"&&w!==null?Reflect.get(w,v):void 0;return typeof R=="string"&&R.length>0?[R]:[]});return {adapter:[...new Set(g)].join(" \xB7 ")||"WebGPU adapter",platform:navigator.platform||navigator.userAgent}})),{scene:e.key,mode:t,...m,frame:p,firstFrameScreenshot:l,screenshot:y,errors:[...s.page,...s.console]}}catch(l){let h=l instanceof Error?l:new Error(String(l));if(/(?:timed?\s*out|timeout)/iu.test(h.message)){let p=this.#n.read(e.key),y=await oe(()=>i.evaluate(()=>{let m=globalThis,u=m.__threeBlocksShaderTools,c=u&&typeof u=="object"?u:void 0;return {documentReadyState:m.document?.readyState??null,parityTargetFrame:Number(m.__threeBlocksParityTargetFrame??0),parityCompletedFrame:Number(m.__threeBlocksParityCompletedFrame??0),readiness:c?.readiness??null,threeRuntimeResources:performance.getEntriesByType("resource").map(w=>w.name).filter(w=>w.includes("three.webgpu"))}}));throw new Error(`${h.message} Last ${t} state for "${e.key}": ${JSON.stringify({page:y,telemetry:p??null})}`)}throw h}finally{await C(()=>o.close());}}async observePublished(e,t){for(let n=0;n<2;n++)try{return await this.#g(e,t)}catch(a){if(n===0&&de(a))continue;throw a}throw new Error(`Published shader observation retry was exhausted for scene "${e.key}".`)}async#g(e,t){if(await this.#w("precompiled",t),!this.#r||!this.#a)throw new Error("Shader browser driver did not start.");let n=await this.#r.newContext({viewport:t.viewport});this.#e.url!==void 0&&await V(n,this.#t,this.#n,"precompiled",t,v(this.#e.runtime.three));let a=await n.newPage(),o=H(a);this.#n.clear(e.key);try{await a.goto(Le(this.#a,e),{waitUntil:"domcontentloaded",timeout:t.timeoutMs}),await Promise.race([a.waitForFunction(t.bridge.legacyLab?"globalThis.__threeBlocks?.compileEnd === true":"globalThis.__threeBlocksShaderTools?.readiness?.compileEnd === true",void 0,{timeout:t.timeoutMs}),o.first.then(p=>Promise.reject(p))]),await ie(a,t,o),L(await A(a,t.bridge.legacyLab),e,t.bridge.legacyLab,this.#s(),v(this.#e.runtime.three)),await x(a,t,2);let i=await se(a),s=await x(a,t,120),l=await se(a),h=L(await A(a,t.bridge.legacyLab),e,t.bridge.legacyLab,this.#s(),v(this.#e.runtime.three));return {scene:e.key,mode:"precompiled",...h,frame:s,firstFrameScreenshot:i,beforeScreenshot:i,screenshot:l,errors:[...o.page,...o.console]}}finally{await C(()=>n.close());}}timingEnvironment(){return this.#f??{adapter:"WebGPU adapter",platform:`${b.platform}/${b.arch}`}}async close(){this.#t.rejectAll(new Error("Shader browser driver closed.")),this.#r&&await C(()=>this.#r?.close()??Promise.resolve());let e=this.#o?.httpServer,t=e?Reflect.get(e,"closeAllConnections"):void 0;if(e&&typeof t=="function"&&Reflect.apply(t,e,[]),this.#o&&await C(()=>this.#o?.close()??Promise.resolve()),this.#i){let n=this.#i;n.closeAllConnections(),await C(()=>new Promise(a=>{n.close(()=>a());}));}if(this.#r=void 0,this.#o=void 0,this.#i=void 0,this.#a=void 0,this.#u=void 0,this.#h=void 0,this.#d=void 0,this.#f=void 0,this.#c=0,this.#l!==void 0&&(await rm(this.#l,{recursive:true,force:true}),this.#l=void 0),this.#m){for(let[n,a]of Object.entries(this.#m))a===void 0?delete b.env[n]:b.env[n]=a;this.#m=void 0;}}};function ct(r){return new O(r)}a(ct,"createPlaywrightShaderDriver");function lt(r){return new O(r)}a(lt,"createStaticPlaywrightShaderDriver");function ut(r){return new O(r)}a(ut,"createAttachedPlaywrightShaderDriver");
76
- export{ve as a,We as b,Z as c,ee as d,je as e,Me as f,G as g,Ve as h,de as i,ct as j,lt as k,ut as l};
@@ -1,93 +0,0 @@
1
- #!/usr/bin/env node
2
- import {b,c}from'./chunk-NE7SC2BX.js';import {a as a$3}from'./chunk-ZT6T2W4B.js';import {a as a$2,c as c$2}from'./chunk-ZDNZCQUQ.js';import {a as a$1,c as c$1,d,f,e,i,j,k}from'./chunk-5L2VS3BN.js';import {a}from'./chunk-HOZDD6PW.js';import _ from'process';import {createServer}from'http';import {createRequire}from'module';import {mkdtemp,rm,lstat,readFile,unlink,mkdir,readdir,realpath}from'fs/promises';import y from'path';import {tmpdir}from'os';import {pathToFileURL}from'url';import {THREE_WEBGPU_R185_COMPATIBILITY,THREE_R186DEV_VERSION,THREE_WEBGPU_R186DEV_COMPATIBILITY,parsePrecompiledManifest,SHADER_HYDRATION_SCHEMA_VERSION,SHADER_RECIPE_SCHEMA_VERSION,SHADER_ADDRESS_SCHEMA_VERSION,PRECOMPILED_MANIFEST_VERSION}from'three-blocks/shaders';import {transformThreeWebgpuProviderHooks,transformThreeWebgpuCaptureInstrumentation}from'three-blocks/vite';function T(r){if(/^0\.185\./u.test(r))return THREE_WEBGPU_R185_COMPATIBILITY;if(r===THREE_R186DEV_VERSION)return THREE_WEBGPU_R186DEV_COMPATIBILITY;throw new Error(`Three.js ${r} is outside the supported shader compatibility contracts.`)}a(T,"shaderCompatibilityForThree");var O=52,Ae="timing.local.json",je="timing.json",de="parity.json",Q=4096,lr=4096;function se(r,e,t=8192){if(typeof r!="string"||r.length===0||r.length>t||/[\u0000\u007f]/u.test(r))throw new Error(`${e} must be a bounded non-empty string.`);return r}a(se,"boundedString");function S(r,e,t=true){if(typeof r!="number"||!Number.isFinite(r)||r<0||t&&!Number.isSafeInteger(r))throw new Error(`${e} must be a non-negative ${t?"integer":"finite number"}.`);return r}a(S,"nonNegativeNumber");function pr(r){if(!a$2(r))throw new Error("Shader capture stats are missing.");let e={buildCalls:S(r.buildCalls,"capture stats.buildCalls"),renderBuilds:S(r.renderBuilds,"capture stats.renderBuilds"),computeBuilds:S(r.computeBuilds,"capture stats.computeBuilds"),registeredBuilds:S(r.registeredBuilds,"capture stats.registeredBuilds"),registeredRenderBuilds:S(r.registeredRenderBuilds,"capture stats.registeredRenderBuilds"),registeredComputeBuilds:S(r.registeredComputeBuilds,"capture stats.registeredComputeBuilds"),buildMs:S(r.buildMs,"capture stats.buildMs",false),syncBuildMs:S(r.syncBuildMs,"capture stats.syncBuildMs",false),asyncBuildElapsedMs:S(r.asyncBuildElapsedMs,"capture stats.asyncBuildElapsedMs",false),precompiledSetupMs:S(r.precompiledSetupMs,"capture stats.precompiledSetupMs",false),maxSyncBuildMs:S(r.maxSyncBuildMs??r.syncBuildMs,"capture stats.maxSyncBuildMs",false),maxPrecompiledSetupMs:S(r.maxPrecompiledSetupMs??r.precompiledSetupMs,"capture stats.maxPrecompiledSetupMs",false),hydrationMs:S(r.hydrationMs??0,"capture stats.hydrationMs",false),maxHydrationMs:S(r.maxHydrationMs??r.hydrationMs??0,"capture stats.maxHydrationMs",false),injected:S(r.injected,"capture stats.injected"),injectedRender:S(r.injectedRender,"capture stats.injectedRender"),injectedCompute:S(r.injectedCompute,"capture stats.injectedCompute"),missed:S(r.missed,"capture stats.missed"),missedRender:S(r.missedRender,"capture stats.missedRender"),missedCompute:S(r.missedCompute,"capture stats.missedCompute"),...Array.isArray(r.missedKeys)&&r.missedKeys.every(t=>typeof t=="string")?{missedKeys:r.missedKeys.slice(0,Q)}:{}};if(e.renderBuilds+e.computeBuilds!==e.buildCalls||e.registeredRenderBuilds+e.registeredComputeBuilds!==e.registeredBuilds||e.injectedRender+e.injectedCompute!==e.injected||e.missedRender+e.missedCompute!==e.missed||e.registeredBuilds>e.buildCalls||Math.abs(e.syncBuildMs+e.asyncBuildElapsedMs-e.buildMs)>.001||e.maxSyncBuildMs>e.syncBuildMs+.001||e.maxPrecompiledSetupMs>e.precompiledSetupMs+.001||e.maxHydrationMs>e.hydrationMs+.001)throw new Error("Shader capture stats totals are inconsistent.");return e}a(pr,"captureStats");function mr(r){if(!Array.isArray(r)||r.length>Q)throw new Error("Shader capture skipped builds are invalid.");return r.map((e,t)=>{if(!a$2(e)||e.kind!=="render"&&e.kind!=="compute")throw new Error(`Shader capture skipped build ${t} is invalid.`);return {kind:e.kind,name:se(e.name,`skipped build ${t} name`,512),reason:se(e.reason,`skipped build ${t} reason`)}})}a(mr,"skippedBuilds");function hr(r){let e=0,t=0,n=0,i=0;for(let s of Object.values(r.entries)){let a=r.states[s];a!==void 0&&((a.vertex!==null||a.fragment!==null)&&e++,a.vertex!==null&&t++,a.fragment!==null&&n++,a.compute!==null&&i++);}return {render:e,vertex:t,fragment:n,compute:i}}a(hr,"shaderCoverage");function it(r,e){if(!a$2(r))throw new Error("Shader capture payload must be an object.");if(r.scene!==e.scene)throw new Error(`Shader capture scene does not match "${e.scene}".`);if(r.protocolVersion!==2)throw new Error("Shader capture protocolVersion must be 2.");let t=T(e.runtime.three);if(r.compatibility!==t)throw new Error(`Shader capture compatibility must be "${t}".`);if(!a$2(r.entries))throw new Error("Shader capture entries must be an object.");if(typeof r.requiresSetup!="boolean")throw new Error("Shader capture requiresSetup must be boolean.");let n=Object.keys(r.entries).length;if(n===0||n>Q)throw new Error(`Shader capture must contain 1...${Q} entries.`);if(!Array.isArray(r.errors)||r.errors.length>lr)throw new Error("Shader capture errors are invalid.");let i=r.errors.map((p,o)=>se(p,`capture error ${o}`,64*1024));if(i.length>0)throw new Error(`Shader capture failed:
3
- - ${i.join(`
4
- - `)}`);let s=mr(r.skipped),a=pr(r.stats),d=a$2(r.timing)?r.timing:void 0,u=d===void 0?void 0:Object.fromEntries(["launch","firstRequest","readiness","lastBuild","settled","posted"].flatMap(p=>{let o=d[p];if(o===void 0)return [];if(typeof o!="number"||!Number.isFinite(o)||o<0)throw new Error(`Shader capture timing.${p} is invalid.`);return [[p,o]]})),m;if(r.provenance!==void 0){if(!a$2(r.provenance)||typeof r.provenance.userAgent!="string"||r.provenance.userAgent.length>1024||typeof r.provenance.adapter!="string"||r.provenance.adapter.length>1024||!Array.isArray(r.provenance.features)||r.provenance.features.length>256||!r.provenance.features.every(p=>typeof p=="string"&&p.length<=128))throw new Error("Shader capture provenance is invalid.");m={userAgent:r.provenance.userAgent,adapter:r.provenance.adapter,features:[...new Set(r.provenance.features)].sort()};}let h=parsePrecompiledManifest({version:PRECOMPILED_MANIFEST_VERSION,scene:e.scene,three:e.runtime.three,threeBlocks:e.runtime.threeBlocks,runtime:{id:t,address:SHADER_ADDRESS_SCHEMA_VERSION,recipe:SHADER_RECIPE_SCHEMA_VERSION,hydration:SHADER_HYDRATION_SCHEMA_VERSION},...r.automatic===void 0?{}:{automatic:r.automatic},requiresSetup:r.requiresSetup,modules:r.modules,nodes:r.nodes,layouts:r.layouts,attributePlans:r.attributePlans,updatePlans:r.updatePlans,requirementPlans:r.requirementPlans,states:r.states,entries:r.entries}),g=hr(h);if(a.registeredRenderBuilds<g.render||a.registeredComputeBuilds<g.compute)throw new Error("Shader capture did not live-build every distinct registered render/compute entry.");return {scene:e.scene,manifest:h,skipped:s,stats:a,coverage:g,...u===void 0?{}:{timing:u},...m===void 0?{}:{provenance:m}}}a(it,"validateShaderCapture");function B(r,e=0){let t=" ".repeat(e),n=" ".repeat(e+1);if(Array.isArray(r))return r.length===0?"[]":r.every(s=>s===null||["number","string","boolean"].includes(typeof s))?JSON.stringify(r):`[
5
- ${r.map(s=>`${n}${B(s,e+1)}`).join(`,
6
- `)}
7
- ${t}]`;if(r!==null&&typeof r=="object"){let s=r,a=Object.keys(s).sort();return a.length===0?"{}":`{
8
- ${a.map(d=>{let u=s[d];return `${n}${JSON.stringify(d)}: ${B(u,e+1)}`}).join(`,
9
- `)}
10
- ${t}}`}let i=JSON.stringify(r);if(i===void 0)throw new Error("Shader artifact contains a non-serializable value.");return i}a(B,"stableStringify");function fr(r){return ["// GENERATED FILE \u2014 do not edit by hand.","// Produced by @three-blocks/devtools.","import type { PrecompiledManifest } from 'three-blocks/shaders';","",`export default ${B(r)} satisfies PrecompiledManifest;`,""].join(`
11
- `)}a(fr,"serializeShaderManifest");function Te(r,e){if(typeof r!="string"||r.length===0||r.length>256||/[\u0000-\u001f\u007f]/u.test(r))throw new Error(`${e} is invalid.`);return r}a(Te,"timingLabel");function ae(r){if(!a$2(r)||r.schemaVersion!==3||r.source!=="latest-local-capture"&&r.source!=="committed-capture"||typeof r.receiptHash!="string"||!/^[a-f0-9]{64}$/u.test(r.receiptHash)||typeof r.measuredAt!="string"||!Number.isFinite(Date.parse(r.measuredAt))||!a$2(r.scenes))throw new Error("Shader timing is invalid.");let e={};for(let[n,i]of Object.entries(r.scenes)){if(n.length===0||n.length>128||!a$2(i))throw new Error("Shader timing scene is invalid.");let s={builds:S(i.builds,`timing ${n}.builds`),setupMeasured:i.setupMeasured===true,liveBuildMs:S(i.liveBuildMs,`timing ${n}.liveBuildMs`,false),precompiledBuildMs:S(i.precompiledBuildMs,`timing ${n}.precompiledBuildMs`,false),avoidedBuildMs:S(i.avoidedBuildMs,`timing ${n}.avoidedBuildMs`,false),runs:S(i.runs,`timing ${n}.runs`),spreadMs:S(i.spreadMs,`timing ${n}.spreadMs`,false)};if(s.runs<1)throw new Error(`Shader timing runs are invalid for scene "${n}".`);if(Math.abs(s.avoidedBuildMs-Math.max(0,s.liveBuildMs-s.precompiledBuildMs))>.001)throw new Error(`Shader timing delta is inconsistent for scene "${n}".`);e[n]=s;}if(Object.keys(e).length===0)throw new Error("Shader timing contains no scenes.");let t={schemaVersion:3,receiptHash:r.receiptHash,measuredAt:r.measuredAt,scenes:e};return r.source==="latest-local-capture"?{...t,source:"latest-local-capture"}:{...t,source:"committed-capture",adapter:Te(r.adapter,"Shader timing adapter"),platform:Te(r.platform,"Shader timing platform")}}a(ae,"parseShaderTiming");function X(r){return /^[a-z0-9][a-z0-9_-]{0,63}$/u.test(r)}a(X,"validParityScene");function Pe(r){return typeof r=="string"&&Number.isFinite(Date.parse(r))}a(Pe,"validParityTimestamp");function ce(r){if(!a$2(r))throw new Error("Shader parity evidence is invalid.");if(r.schemaVersion===1){if(typeof r.receiptHash!="string"||!/^[a-f0-9]{64}$/u.test(r.receiptHash)||!Pe(r.verifiedAt)||!Array.isArray(r.scenes)||r.scenes.length===0||r.scenes.length>64||!r.scenes.every(n=>typeof n=="string"&&X(n)))throw new Error("Shader parity evidence is invalid.");return {schemaVersion:1,receiptHash:r.receiptHash,verifiedAt:r.verifiedAt,scenes:[...new Set(r.scenes)].sort()}}if(r.schemaVersion!==2||!a$2(r.scenes))throw new Error("Shader parity evidence is invalid.");let e=Object.entries(r.scenes);if(e.length===0||e.length>64)throw new Error("Shader parity evidence is invalid.");let t={};for(let[n,i]of e.sort(([s],[a])=>s.localeCompare(a))){if(!X(n)||!a$2(i)||typeof i.fingerprint!="string"||!/^[a-f0-9]{64}$/u.test(i.fingerprint)||!Pe(i.verifiedAt))throw new Error("Shader parity evidence is invalid.");t[n]={fingerprint:i.fingerprint,verifiedAt:i.verifiedAt};}return {schemaVersion:2,scenes:t}}a(ce,"parseShaderParityEvidence");function oe(r,e){let t=r.scenes[e];if(t===void 0)throw new Error(`Shader receipt has no scene "${e}" for parity evidence.`);return c$1(B({runtime:{three:r.runtime.three,threeBlocks:r.runtime.threeBlocks,threeBlocksShaderClosure:r.runtime.threeBlocksShaderClosure},...r.tool===void 0?{}:{tool:r.tool},scene:t}))}a(oe,"shaderSceneParityFingerprint");async function ke(r,e,t,n){let i=y.join(r,t);try{if(!await d(i))return;let s=await lstat(i);if(s.isSymbolicLink()||!s.isFile()||s.size>1024*1024)return;let a=ae(JSON.parse(await readFile(i,"utf8")));return a.source===n&&a.receiptHash===c$1(e)?a:void 0}catch{return}}a(ke,"readShaderTimingFile");async function st(r,e){return await ke(r,e,Ae,"latest-local-capture")??await ke(r,e,je,"committed-capture")}a(st,"readShaderTiming");async function Oe(r,e){let t=y.join(r,de);try{if(!await d(t))return;let n=await lstat(t);if(n.isSymbolicLink()||!n.isFile()||n.size>1024*1024)return;let i=ce(JSON.parse(await readFile(t,"utf8"))),s=c$2(JSON.parse(Buffer.from(e).toString("utf8"))),a={};if(i.schemaVersion===1){if(i.receiptHash!==c$1(e))return;for(let d of i.scenes)s.scenes[d]!==void 0&&(a[d]={fingerprint:oe(s,d),verifiedAt:i.verifiedAt});}else for(let[d,u]of Object.entries(i.scenes))s.scenes[d]===void 0||u.fingerprint!==oe(s,d)||(a[d]=u);return Object.keys(a).length===0?void 0:{schemaVersion:2,scenes:a}}catch{return}}a(Oe,"readShaderParityEvidence");async function Ie(r,e,t){let n=await Z(r),i=y.join(n,"meta.json"),s=await lstat(i);if(s.isSymbolicLink()||!s.isFile())throw new Error("Shader receipt must be a regular file before timing.");let a=await readFile(i),d=new Date().toISOString(),u=Object.fromEntries(Object.entries(e).sort(([g],[p])=>g.localeCompare(p))),m=ae({schemaVersion:3,receiptHash:c$1(a),measuredAt:d,source:"latest-local-capture",scenes:u});if(await f(y.join(n,Ae),`${B(m)}
12
- `),t===void 0)return {local:m};let h=ae({schemaVersion:3,receiptHash:c$1(a),measuredAt:d,source:"committed-capture",adapter:t.adapter,platform:t.platform,scenes:u});return await f(y.join(n,je),`${B(h)}
13
- `),{local:m,committed:h}}a(Ie,"writeShaderTimings");async function at(r,e){return (await Ie(r,e)).local}a(at,"writeShaderLocalTiming");async function ot(r,e,t){if(e.length===0||e.length>64||e.some(p=>!X(p)))throw new Error("Shader parity evidence must contain 1...64 valid scene keys.");let n=await Z(r),i=y.join(n,"meta.json"),s=await lstat(i);if(s.isSymbolicLink()||!s.isFile())throw new Error("Shader receipt must be a regular file before parity evidence.");let a=await readFile(i);if(t!==void 0&&c$1(a)!==c$1(t))throw new Error("Shader receipt changed during browser parity verification; completed observations were not attached to the new receipt.");let d=c$2(JSON.parse(a.toString("utf8"))),u=await Oe(n,a),m=new Date().toISOString(),h={...u?.scenes};for(let p of [...new Set(e)].sort())h[p]={fingerprint:oe(d,p),verifiedAt:m};let g=ce({schemaVersion:2,scenes:h});return await f(y.join(n,de),`${B(g)}
14
- `),g}a(ot,"writeShaderParityEvidence");async function dt(r,e,t){if(e.length===0||e.length>64||e.some(h=>!X(h)))throw new Error("Shader parity invalidation must contain 1...64 valid scene keys.");let n=await Z(r),i=await readFile(y.join(n,"meta.json"));if(c$1(i)!==c$1(t))throw new Error("Shader receipt changed before prior parity evidence could be invalidated.");let s=await Oe(n,i);if(s===void 0)return;let a=new Set(e),d=Object.fromEntries(Object.entries(s.scenes).filter(([h])=>!a.has(h))),u=y.join(n,de);if(Object.keys(d).length===0){await unlink(u).catch(h=>{if(!a$2(h)||h.code!=="ENOENT")throw h});return}let m=ce({schemaVersion:2,scenes:d});await f(u,`${B(m)}
15
- `);}a(dt,"removeShaderParityEvidence");async function ct(r,e,t){let n=await Ie(r,e,t);if(n.committed===void 0)throw new Error("Committed shader timing was not written.");return {local:n.local,committed:n.committed}}a(ct,"writeShaderTimingTwins");async function Ce(r){if(!await d(r)){await mkdir(r);return}let e=await lstat(r);if(e.isSymbolicLink()||!e.isDirectory())throw new Error(`Shader artifact path is not a real directory: ${r}.`)}a(Ce,"assertDirectory");async function Z(r){let e=y.resolve(r),t=y.join(e,".three-blocks");await Ce(t);let n=y.join(t,"shaders");return await Ce(n),n}a(Z,"artifactRoot");async function ut(r){let e$1=await Z(r.root),t=T(r.runtime.three),n=y.resolve(r.root),i$1=y.resolve(n,r.publicDirectory??"public");if(!e(n,i$1)||i$1===n)throw new Error("Shader public directory must stay inside the project root.");let s=y.join(i$1,"three-blocks","shaders");await mkdir(s,{recursive:true}),await i(n,s,"Shader static-asset directory");let a={},d=[];for(let o of [...r.scenes].sort((l,f)=>l.key.localeCompare(f.key))){let l=r.captures.get(o.key),f$1=r.inputs.get(o.key);if(f$1===void 0)throw new Error(`Shader input matrix is missing scene "${o.key}".`);if(l===void 0){let E=r.previousReceipt?.scenes[o.key];if(E===void 0)throw new Error(`Capture matrix is missing scene "${o.key}".`);let F=await readFile(y.join(e$1,E.artifact));if(c$1(F)!==E.artifactHash)throw new Error(`Preserved shader artifact checksum differs for scene "${o.key}".`);if(E.asset!==void 0&&E.assetHash!==void 0){let N=await readFile(y.join(i$1,E.asset));if(c$1(N)!==E.assetHash)throw new Error(`Preserved static shader manifest checksum differs for scene "${o.key}".`)}a[o.key]={...E,inputs:Object.fromEntries(Object.entries(f$1).sort(([N],[z])=>N.localeCompare(z)))},d.push(E.artifact),E.asset!==void 0&&d.push(y.relative(n,y.join(i$1,E.asset)).split(y.sep).join("/"));continue}if(l.scene!==o.key||l.manifest.scene!==o.key)throw new Error(`Capture matrix scene "${o.key}" is inconsistent.`);let w=`${o.key}.webgpu.ts`,R=fr(l.manifest);await f(y.join(e$1,w),R),d.push(w);let P=`three-blocks/shaders/${o.key}.json`,k=`${B(l.manifest)}
16
- `;await f(y.join(i$1,P),k),d.push(y.relative(n,y.join(i$1,P)).split(y.sep).join("/"));let J=l.skipped.filter(E=>E.kind==="render").length,C=l.skipped.length-J;a[o.key]={artifact:w,artifactHash:c$1(R),asset:P,assetHash:c$1(k),inputs:Object.fromEntries(Object.entries(f$1).sort(([E],[F])=>E.localeCompare(F))),coverage:l.coverage,bytes:Buffer.byteLength(R),skipped:{render:J,compute:C}};}let u=[...r.captures.values()].find(o=>o.provenance!==void 0)?.provenance??r.previousReceipt?.runtime.capture,m={schemaVersion:2,runtime:{...r.runtime,...u===void 0?{}:{capture:u}},tool:{name:"@three-blocks/devtools",version:a$3,compatibility:t,transform:O,address:SHADER_ADDRESS_SCHEMA_VERSION,recipe:SHADER_RECIPE_SCHEMA_VERSION,hydration:SHADER_HYDRATION_SCHEMA_VERSION},scenes:a},h=new Set(d);for(let o of await readdir(e$1,{withFileTypes:true}))if(!(!o.name.endsWith(".webgpu.ts")||h.has(o.name))){if(o.isSymbolicLink()||!o.isFile())throw new Error(`Orphan shader artifact is not a regular file: ${o.name}.`);await unlink(y.join(e$1,o.name));}let g=new Set(r.scenes.map(o=>`${o.key}.json`)),p=new Set(Object.values(r.previousReceipt?.scenes??{}).map(o=>o.asset===void 0?void 0:y.posix.basename(o.asset)).filter(o=>o!==void 0));try{let o=c$2(JSON.parse(await readFile(y.join(e$1,"meta.json"),"utf8")));for(let l of Object.values(o.scenes))l.asset!==void 0&&p.add(y.posix.basename(l.asset));}catch{}for(let o of await readdir(s,{withFileTypes:true}))if(!(!o.name.endsWith(".json")||g.has(o.name))&&p.has(o.name)){if(o.isSymbolicLink()||!o.isFile())throw new Error(`Orphan shader static asset is not a regular file: ${o.name}.`);await unlink(y.join(s,o.name));}return await f(y.join(e$1,"meta.json"),`${B(m)}
17
- `),d.push("meta.json"),{directory:e$1,receipt:m,files:d}}a(ut,"writeShaderArtifacts");var Le="three-blocks.shader-capture.runtime.v1";var G;async function $(){G===void 0&&(G=(async()=>{let e=createRequire(y.join(process.cwd(),"package.json")).resolve("@three-blocks/devtools/browser/shader-capture"),t=y.resolve(y.dirname(e),"../..");return (await j(t,e,a$1.metadata,"Shader capture browser runtime")).data.toString("utf8")})());let r=G;try{return await r}catch(e){throw G===r&&(G=void 0),e}}a($,"loadShaderCaptureRuntimeSource");var De="virtual:three-blocks-shader-capture-client",$e="\0three-blocks:shader-capture-client",le="virtual:three-blocks-shader-capture-runtime",Fe="\0three-blocks:shader-capture-runtime";async function He(){let r=await $(),e=r.replace(/\bexport\{[^{}]*\};?\s*$/u,"");if(e===r)throw new Error("Shader capture browser runtime no longer has the expected final ESM export list.");return e}a(He,"loadShaderCaptureRuntimeScriptSource");function br(r){let e=r.split("?",1)[0];return e===void 0?false:e.split(y.sep).join("/").endsWith("/build/three.webgpu.js")}a(br,"isThreeWebGPUModule");function Ue(r){let e=/^(\d+)\.(\d+)\.(\d+)(?:[-+].*)?$/u.exec(r);return e?.[1]==="0"&&e[2]==="185"}a(Ue,"supportedVersion");function Er(r,e,t={}){if(!Ue(e))throw new Error(`Shader provider transform ${THREE_WEBGPU_R185_COMPATIBILITY} supports Three.js 0.185.x; received "${e}".`);let n=transformThreeWebgpuProviderHooks(r,{threeVersion:e,...t.threeRevision===void 0?{}:{threeRevision:t.threeRevision},id:"three/build/three.webgpu.js"}),i=n.state==="already-applied",s=n.code;return t.instrumentCapture&&(s=transformThreeWebgpuCaptureInstrumentation(s,{...t.captureRuntimeImport===void 0?{}:{runtimeImport:t.captureRuntimeImport}}).code),{code:s,alreadyPresent:i,captureApplied:t.instrumentCapture===true}}a(Er,"applyShaderProviderTransform");var Rr=/this\.trackTimestamp\s*=\s*\(\s*parameters\.trackTimestamp\s*===\s*true\s*\);/gu,vr="Object.defineProperty( this, 'trackTimestamp', { get: () => false, set: () => {} } );";function Ve(r,e={}){if(!Ue(r))throw new Error(`Shader provider transform ${THREE_WEBGPU_R185_COMPATIBILITY} supports Three.js 0.185.x; received "${r}".`);let t={seen:false,applied:false,alreadyPresent:false};return {plugin:{name:"three-blocks:shader-provider-transform",enforce:"pre",config(){return {optimizeDeps:{exclude:["three","three/webgpu","three/tsl"]},resolve:{dedupe:["three"]}}},resolveId(i){return e.capture&&i===De?$e:e.capture&&i===le?Fe:null},async load(i){return e.capture?i===Fe?$():i===$e?[`export * from '${le}';`,`import { configureThreeBlocksShaderCapture } from '${le}';`,`configureThreeBlocksShaderCapture( ${JSON.stringify({capture:e.capture.capture,forceLive:e.capture.forceLive,settleFrames:e.capture.settleFrames,settleTimeoutMs:e.capture.settleTimeoutMs,visibilityGuard:e.capture.visibilityGuard,captureId:e.capture.captureId,sessionKey:e.capture.sessionKey,token:e.capture.token,readiness:e.capture.readiness??{},transform:O})} );`].join(`
18
- `):null:null},transform(i,s){if(!br(s))return null;t.seen=true,t.id=s;try{let a=Er(i,r,{instrumentCapture:e.capture!==void 0,...e.capture!==void 0?{captureRuntimeImport:De}:{}}),d=e.disableTimestampQueries===!0?a.code.replace(Rr,vr):a.code;if(e.disableTimestampQueries===!0&&d===a.code)throw new Error("Three.js timestamp tracking anchor drifted; refusing software WebGPU capture.");return t.applied=!0,t.alreadyPresent=a.alreadyPresent,t.captureApplied=a.captureApplied,d===i?null:{code:d,map:null}}catch(a){throw t.error=a instanceof Error?a.message:String(a),a}}},status:t}}a(Ve,"createShaderProviderTransform");function pe(r){if(r.error)throw new Error(r.error);if(!r.seen||!r.applied)throw new Error(`The version-gated shader provider transform was not applied (${r.seen?"module seen":"three/webgpu not seen"}).`)}a(pe,"assertShaderProviderTransform");var Qe="/__three-blocks/shaders/capture",te="/__three-blocks/shaders/telemetry",Xe="/__three-blocks/shaders/runtime.js",Ze="/__three-blocks/shaders/bootstrap.js",er="/__three-blocks/shaders/bridge.js",rr=a$1.manifest*2,fe=/^[a-z0-9][a-z0-9_-]{0,63}$/u,tr=64,nr=2e3,xr=[/is not valid JSON/iu,/WebGPU is experimental/iu];async function Ar(){try{return (await import('playwright')).chromium}catch(r){throw new Error('Shader browser work requires the optional "playwright" package. Install it in the project and run `npx playwright install chromium`.',{cause:r})}}a(Ar,"loadChromium");async function jr(r){let e;try{e=createRequire(y.join(r,"package.json")).resolve("vite");}catch(n){throw new Error("Shader capture requires Vite in the target project.",{cause:n})}let t=await import(pathToFileURL(e).href);if(typeof t.createServer!="function")throw new Error(`The target project's Vite entry does not export createServer(): ${e}`);return t.createServer}a(jr,"loadProjectCreateServer");var ye=class{static{a(this,"CaptureInbox");}#e=new Map;#r=new Map;wait(e,t){let n=this.#r.get(e);if(n!==void 0)return this.#r.delete(e),Promise.resolve(n);if(this.#e.has(e))throw new Error(`A shader capture is already waiting for scene "${e}".`);return new Promise((i,s)=>{let a=setTimeout(()=>{this.#e.delete(e),s(new Error(`Shader capture "${e}" timed out after ${t}ms.`));},t);this.#e.set(e,{resolve:i,reject:s,timer:a});})}receive(e){if(!a$2(e)||typeof e.scene!="string"||!fe.test(e.scene))throw new Error("Capture POST has no safe scene key.");if(!this.#r.has(e.scene)&&!this.#e.has(e.scene)&&this.#r.size>=tr)throw new Error("Capture POST exceeds the scene inbox limit.");let t=this.#e.get(e.scene);t?(clearTimeout(t.timer),this.#e.delete(e.scene),t.resolve(e)):this.#r.set(e.scene,e);}cancel(e,t){let n=this.#e.get(e);n&&(clearTimeout(n.timer),this.#e.delete(e),n.reject(t));}rejectAll(e){for(let t of this.#e.values())clearTimeout(t.timer),t.reject(e);this.#e.clear(),this.#r.clear();}};async function Or(r,e){let t=await Promise.race([e.then(n=>({kind:"capture",value:n})),r.then(()=>({kind:"navigation"}))]);return t.kind==="capture"?t.value:e}a(Or,"waitForShaderCaptureAcrossNavigation");var ge=class{static{a(this,"TelemetryHub");}#e=new Map;#r=new Map;markFirstRequest(e){fe.test(e)&&!this.#r.has(e)&&this.#r.set(e,Date.now());}firstRequest(e){return this.#r.get(e)}receive(e){if(!a$2(e)||typeof e.scene!="string"||!fe.test(e.scene))throw new Error("Shader telemetry has no bounded scene key.");if(!this.#e.has(e.scene)&&this.#e.size>=tr)throw new Error("Shader telemetry exceeds the scene limit.");this.#e.set(e.scene,e);}read(e){return this.#e.get(e)}clear(e){this.#e.delete(e),this.#r.delete(e);}},Ir=a(async(r,e,t,n,i)=>{let s=0;for(;r.__threeBlocksParityUsesAnimationLoop!==true&&s<e;)await n(),s+=1;if(r.__threeBlocksParityUsesAnimationLoop===true){let a=Number(r.__threeBlocksParityCompletedFrame||0),d=Number(t),u=Number.isSafeInteger(d)&&d>=a?d:a+e;for(r.__threeBlocksParityTargetFrame=u;Number(r.__threeBlocksParityCompletedFrame||0)<u;)await n();}return await i(),Number(r.__threeBlocksParityCompletedFrame||0)},"settleShaderParityFrames");function Se(r){return `(() => {
19
- const root = globalThis;
20
- const scene = new URL(location.href).searchParams.get('captureId')
21
- || 'default';
22
- const randomSeed = (value) => {
23
- let state = 2166136261;
24
- for (let index = 0; index < value.length; index++) state = Math.imul(state ^ value.charCodeAt(index), 16777619) >>> 0;
25
- return state === 0 ? 0x9e3779b9 : state;
26
- };
27
- const advanceRandom = (state) => {
28
- state ^= state << 13;
29
- state ^= state >>> 17;
30
- state ^= state << 5;
31
- return state >>> 0;
32
- };
33
- const parityMode = new URL(location.href).searchParams.get('threeBlocksShaderMode');
34
- if (parityMode === 'live' || parityMode === 'precompiled') {
35
- root.__threeBlocksParityEpoch = 1700000000000;
36
- root.__threeBlocksParityTime = 0;
37
- Date.now = () => root.__threeBlocksParityEpoch + Number(root.__threeBlocksParityTime || 0);
38
- }
39
- const randomStreams = new Map();
40
- Math.random = () => {
41
- const stackLine = String(new Error().stack || '').split('\\n')[2] || 'unknown';
42
- const originIndex = stackLine.indexOf(location.origin);
43
- const callsite = (originIndex >= 0 ? stackLine.slice(0, originIndex) : stackLine).trim() || 'anonymous';
44
- const next = advanceRandom(randomStreams.get(callsite) ?? randomSeed(scene + '|' + callsite));
45
- randomStreams.set(callsite, next);
46
- return next / 4294967296;
47
- };
48
- const readiness = { workerReady: false, assetsReady: false, textReady: false, compileEnd: false, firstFrame: false };
49
- const stats = { buildCalls: 0, renderBuilds: 0, computeBuilds: 0, registeredBuilds: 0, registeredRenderBuilds: 0, registeredComputeBuilds: 0, buildMs: 0, syncBuildMs: 0, asyncBuildElapsedMs: 0, precompiledSetupMs: 0, maxSyncBuildMs: 0, maxPrecompiledSetupMs: 0, hydrationMs: 0, maxHydrationMs: 0, injected: 0, injectedRender: 0, injectedCompute: 0, missed: 0, missedRender: 0, missedCompute: 0, missedKeys: [] };
50
- const settleParityFrames = ${Ir.toString()};
51
- const settle = (frames, requestedTarget) => settleParityFrames(
52
- root,
53
- frames,
54
- requestedTarget,
55
- () => new Promise((resolve) => requestAnimationFrame(resolve)),
56
- () => new Promise((resolve) => setTimeout(resolve, 100)),
57
- );
58
- const bridge = { protocolVersion: 1, compatibility: ${JSON.stringify(r)}, transform: ${O}, readiness, stats, settle };
59
- root.__threeBlocksShaderTools = bridge;
60
- requestAnimationFrame(() => requestAnimationFrame(() => { readiness.firstFrame = true; }));
61
- const poll = async () => {
62
- try {
63
- const response = await fetch('/__three-blocks/shaders/telemetry?scene=' + encodeURIComponent(scene), { cache: 'no-store' });
64
- if (response.status !== 204 && response.ok) {
65
- const payload = await response.json();
66
- if (payload.protocolVersion !== 1 || payload.compatibility !== bridge.compatibility || payload.transform !== bridge.transform) throw new Error('incompatible shader telemetry');
67
- Object.assign(stats, payload.stats);
68
- readiness.workerReady = true;
69
- if (payload.settled === true) {
70
- readiness.assetsReady = true;
71
- readiness.textReady = true;
72
- readiness.compileEnd = true;
73
- }
74
- const smoke = root.__threeBlocksSmoke && typeof root.__threeBlocksSmoke === 'object' ? root.__threeBlocksSmoke : { protocolVersion: 1, worker: { offscreenCanvas: true, visible: true }, readiness: {} };
75
- smoke.readiness = { ...(smoke.readiness || {}), ...readiness };
76
- root.__threeBlocksSmoke = smoke;
77
- }
78
- } catch {}
79
- setTimeout(poll, 40);
80
- };
81
- void poll();
82
- })();`}a(Se,"publicBridgeScript");function ir(r,e,t,n,i=false){let s=new URL(r.url??"/","http://three-blocks.invalid"),a=s.pathname;if(i&&r.method==="GET"&&/^\/three-blocks\/shaders\/[a-z0-9][a-z0-9_-]{0,63}\.json$/u.test(a))return e.statusCode=204,e.end(),true;if(a===te&&r.method==="GET"){let p=s.searchParams.get("scene")??"",o=n.read(p);return o===void 0?(e.statusCode=204,e.end()):(e.statusCode=200,e.setHeader("Content-Type","application/json"),e.end(JSON.stringify(o))),true}let d=a===Qe,u=a===te;if(!d&&!u)return false;if(r.method!=="POST")return e.statusCode=405,e.end("POST required"),true;let m=[],h=0,g=false;return r.on("data",p=>{h+=p.byteLength,h>rr?g=true:m.push(p);}),r.on("end",()=>{if(g){e.statusCode=413,e.end("capture payload too large");return}try{let p=JSON.parse(Buffer.concat(m).toString("utf8"));u?n.receive(p):t.receive(p),e.statusCode=204,e.end();}catch(p){e.statusCode=400,e.end(p instanceof Error?p.message:String(p));}}),true}a(ir,"handleCaptureEndpoint");function Lr(r,e,t,n){return {name:"three-blocks:shader-capture-endpoint",transformIndexHtml(){return [{tag:"script",children:Se(n),injectTo:"head-prepend"}]},configureServer(i){i.middlewares.use((s,a,d)=>{let m=new URL(s.url??"/","http://three-blocks.invalid").searchParams.get("captureId");m!==null&&e.markFirstRequest(m),!ir(s,a,r,e,t)&&d();});}}}a(Lr,"captureEndpointPlugin");function We(r,e,t){let n=new URL(e.url,r);for(let[i,s]of Object.entries(t))n.searchParams.set(i,s);return n.href}a(We,"browserUrl");function Dr(r,e){let t=new URL(e.url,r);for(let n of ["capture","precompiled"])t.searchParams.delete(n);return t.searchParams.set("captureId",e.key),t.searchParams.set("threeBlocksShaderMode","precompiled"),t.searchParams.set("tbStats","1"),t.href}a(Dr,"publishedBrowserUrl");function qe(r){return xr.some(e=>e.test(r))}a(qe,"knownNoise");async function L(r){let e;try{await Promise.race([r(),new Promise(t=>{e=setTimeout(t,nr);})]);}catch{}finally{e&&clearTimeout(e);}}a(L,"closeBrowserResource");async function Ke(r){let e;try{return await Promise.race([r().catch(()=>null),new Promise(t=>{e=setTimeout(()=>t(null),nr);})])}finally{e!==void 0&&clearTimeout(e);}}a(Ke,"readPageDiagnostic");function me(r){let e=a(()=>{},"resolveFirst"),t=new Promise(a=>{e=a;}),n={console:[],page:[],first:t},i=false,s=a(a=>{i||(i=true,e(new Error(a)));},"report");return r.on("console",a=>{let d=a.type()==="warning"&&/\[three-blocks\/shaders\].*(?:has no entry|manifest miss|hydration)/iu.test(a.text());if(a.type()!=="error"&&!d||qe(a.text()))return;let u=a.location().url,m=u.length>0?`${a.text()} (${u})`:a.text();n.console.push(m),s(`Browser console ${d?"warning":"error"}: ${m}`);}),r.on("pageerror",a=>{if(qe(a.message))return;let d=a.stack||a.message;n.page.push(d),s(`Browser page error: ${d}`);}),r.on("crash",()=>s("Browser page crashed before shader capture completed.")),r.on("close",()=>s("Browser page closed before shader capture completed.")),n}a(me,"collectErrors");function W(r,e,t=false){return typeof r[e]=="boolean"?r[e]:t}a(W,"booleanField");function $r(r){if(!a$2(r))throw new Error("Browser shader stats are unavailable.");let e=a((t,n=true)=>{let i=r[t];if(typeof i!="number"||!Number.isFinite(i)||i<0||n&&!Number.isSafeInteger(i))throw new Error(`Browser shader stats.${t} is invalid.`);return i},"read");return {buildCalls:e("buildCalls"),renderBuilds:e("renderBuilds"),computeBuilds:e("computeBuilds"),registeredBuilds:e("registeredBuilds"),registeredRenderBuilds:e("registeredRenderBuilds"),registeredComputeBuilds:e("registeredComputeBuilds"),buildMs:e("buildMs",false),syncBuildMs:e("syncBuildMs",false),asyncBuildElapsedMs:e("asyncBuildElapsedMs",false),precompiledSetupMs:e("precompiledSetupMs",false),maxSyncBuildMs:e("maxSyncBuildMs",false),maxPrecompiledSetupMs:e("maxPrecompiledSetupMs",false),hydrationMs:e("hydrationMs",false),maxHydrationMs:e("maxHydrationMs",false),injected:e("injected"),injectedRender:e("injectedRender"),injectedCompute:e("injectedCompute"),missed:e("missed"),missedRender:e("missedRender"),missedCompute:e("missedCompute"),...Array.isArray(r.missedKeys)&&r.missedKeys.every(t=>typeof t=="string")?{missedKeys:r.missedKeys}:{}}}a($r,"parseStats");function ee(r,e,t,n,i){if(!a$2(r))throw new Error("The page did not expose the public shader devtools bridge.");if(!t&&r.protocolVersion!==1)throw new Error(`Scene "${e.key}" exposed an unsupported shader bridge protocol.`);let s=r.readiness;if(!a$2(s))throw new Error("The shader bridge readiness snapshot is invalid.");let a={workerReady:W(s,"workerReady"),assetsReady:W(s,"assetsReady"),textReady:e.requiresText?W(s,"textReady"):true,compileEnd:W(s,"compileEnd"),firstFrame:W(s,"firstFrame",t)};if(!a.workerReady||!a.assetsReady||!a.textReady||!a.compileEnd)throw new Error(`Scene "${e.key}" did not reach worker/assets/text/compile readiness.`);let d=t?i:r.compatibility,u=t?O:r.transform;if(d!==i||u!==O)throw new Error(`Scene "${e.key}" exposed incompatible shader bridge metadata.`);return pe(n),{compatibility:i,transform:u,readiness:a,stats:$r(r.stats)}}a(ee,"parseBridge");async function re(r,e){return r.evaluate(t=>{let n=globalThis;if(!t)return n.__threeBlocksShaderTools??null;let i=n.__threeBlocks,s=n.__threeBlocksTslStats;if(!i||typeof i!="object")return null;let a=i;return {readiness:{workerReady:a.workerReady===true,assetsReady:a.loadEnd===true||a.assetsReady===true,textReady:a.textReady===true,compileEnd:a.compileEnd===true,firstFrame:true},stats:s}},e)}a(re,"readBridge");async function q(r,e,t,n){return r.evaluate(async i=>{let a$1=globalThis.__threeBlocksShaderTools;if(a$1&&typeof a$1=="object"){let m=Reflect.get(a$1,"settle");if(typeof m=="function"){let h=await m(i.frames,i.targetFrame);return typeof h=="number"&&Number.isSafeInteger(h)?h:0}}if(!i.legacy||!i.modulePath)throw new Error("The public shader bridge does not provide deterministic settle().");let d=await import(i.modulePath);if(!d.store||typeof d.store!="object")throw new Error("Legacy deterministic store is unavailable.");let u=d.store;return u.recordFrameCount=0,u.recordFrameRate=60,u.recordTotalFrames=i.frames,u.recording=true,await new Promise((m,h)=>{let g=Date.now(),p=a(()=>{if(u.recording===false)return m();if(Date.now()-g>i.timeoutMs)return h(new Error("Legacy deterministic settle timed out."));setTimeout(p,25);},"poll");p();}),0},{frames:t,targetFrame:n,legacy:e.bridge.legacyLab,modulePath:e.bridge.deterministicModule??null,timeoutMs:e.timeoutMs})}a(q,"settlePage");async function Je(r,e,t){e.readiness.selector===void 0&&e.readiness.global===void 0||await Promise.race([r.waitForFunction(n=>{let i=globalThis;if(n.selector!==void 0&&i.document?.querySelector(n.selector)==null)return false;if(n.global===void 0)return true;let s=i;for(let u of n.global.split(".")){if((typeof s!="object"||s===null)&&typeof s!="function")return false;s=Reflect.get(s,u);}if(s===true)return true;if(typeof s!="object"||s===null||typeof Reflect.get(s,"then")!="function")return false;let a=i.__threeBlocksReadinessState,d=a instanceof Map?a:new Map;return a instanceof Map||(i.__threeBlocksReadinessState=d),d.has(s)||(d.set(s,false),Promise.resolve(s).then(()=>d.set(s,true),()=>d.set(s,false))),d.get(s)===true},e.readiness,{timeout:e.timeoutMs}),t.first.then(n=>Promise.reject(n))]);}a(Je,"waitForConfiguredReadiness");async function ze(r){let e=r.locator("canvas"),n=(await e.evaluateAll(i=>i.map((s,a)=>{let d=s.getBoundingClientRect();return {index:a,area:Math.max(0,d.width)*Math.max(0,d.height)}}))).sort((i,s)=>s.area-i.area)[0];if(n===void 0||n.area<=0)throw new Error("Published page has no visible renderer canvas.");return Buffer.from(await e.nth(n.index).screenshot({type:"png"}))}a(ze,"primaryCanvasScreenshot");async function he(r,e,t,n,i,s){let a=sr(n,i),d=await He(),u=`(() => {
83
- const runtime = globalThis[Symbol.for(${JSON.stringify(Le)})];
84
- if (!runtime || typeof runtime.configureThreeBlocksShaderCapture !== 'function') {
85
- throw new Error('@three-blocks/devtools attached shader capture runtime is incompatible.');
86
- }
87
- runtime.configureThreeBlocksShaderCapture(${JSON.stringify(a).replaceAll("<","\\u003c")});
88
- })();`;await r.addInitScript({content:`${d}
89
- ${u}`}),await r.addInitScript({content:Se(s)}),await r.route("**/*",async m=>{let h=m.request(),g=new URL(h.url()),p=g.pathname;if(h.method()==="GET"&&n!=="precompiled"&&/^\/three-blocks\/shaders\/[a-z0-9][a-z0-9_-]{0,63}\.json$/u.test(p)){await m.fulfill({status:204});return}if(p===te&&h.method()==="GET"){let f=t.read(g.searchParams.get("scene")??"");await m.fulfill(f===void 0?{status:204}:{status:200,contentType:"application/json",body:JSON.stringify(f)});return}let o=p===Qe,l=p===te;if((o||l)&&h.method()==="POST"){let f=h.postDataBuffer()??Buffer.alloc(0);if(f.byteLength>rr){await m.fulfill({status:413,body:"capture payload too large"});return}try{let w=JSON.parse(f.toString("utf8"));l?t.receive(w):e.receive(w),await m.fulfill({status:204});}catch(w){await m.fulfill({status:400,body:w instanceof Error?w.message:String(w)});}return}await m.continue();});}a(he,"configureAttachedContext");var Fr=Object.freeze({".avif":"image/avif",".css":"text/css; charset=utf-8",".gif":"image/gif",".html":"text/html; charset=utf-8",".ico":"image/x-icon",".jpeg":"image/jpeg",".jpg":"image/jpeg",".js":"text/javascript; charset=utf-8",".json":"application/json; charset=utf-8",".mjs":"text/javascript; charset=utf-8",".mp4":"video/mp4",".png":"image/png",".svg":"image/svg+xml",".wasm":"application/wasm",".webm":"video/webm",".webp":"image/webp",".woff":"font/woff",".woff2":"font/woff2"});function Nr(r){let e=[`<script src="${er}"></script>`,`<script type="module" src="${Ze}"></script>`].join(""),t=/<head(?:\s[^>]*)?>/iu.exec(r);return t===null?`${e}${r}`:`${r.slice(0,t.index+t[0].length)}${e}${r.slice(t.index+t[0].length)}`}a(Nr,"injectStaticShaderCaptureHtml");function Hr(r,e){let t=sr(r,e);return [`import { configureThreeBlocksShaderCapture } from ${JSON.stringify(Xe)};`,`configureThreeBlocksShaderCapture( ${JSON.stringify(t).replaceAll("<","\\u003c")} );`].join(`
90
- `)}a(Hr,"staticCaptureBootstrap");function sr(r,e){return {capture:r==="capture",forceLive:r!=="precompiled",settleFrames:e.settleFrames,settleTimeoutMs:e.settleTimeoutMs??3e4,readiness:e.readiness,transform:O}}a(sr,"shaderCaptureConfiguration");async function Ur(r,e){let t=await k(r,e,a=>/\.(?:c|m)?js$/u.test(a),16384),n=false,i=false,s;for(let a of t){let d=(await j(r,a,a$1.texture,"Static application JavaScript")).data.toString("utf8");if(d.includes("nodeBuilderStateProvider")&&(n=true),d.includes("three-blocks.shader-capture.runtime.v1")&&(i=true,s??=a),n&&i)break}if(!n||!i)throw new Error("The static build does not contain the Three.js shader capture transform. Run `shaders capture` without an explicit driver or URL to preview adapter wiring and build automatically, or add the manual adapter from the package README and rebuild.");return {seen:true,applied:true,alreadyPresent:false,captureApplied:true,...s===void 0?{}:{id:s}}}a(Ur,"inspectStaticCaptureTransform");async function Vr(r,e$1){let t;try{t=decodeURIComponent(e$1);}catch{return}if(t.includes("\0"))return;let n=t.replace(/^\/+/u,""),i=y.resolve(r,n.length===0?"index.html":n);if(!e(r,i)||i===r||(await d(i)&&(await lstat(i)).isDirectory()&&(i=y.join(i,"index.html")),!await d(i)&&y.extname(i).length===0&&(i=y.join(r,"index.html")),!await d(i)))return;let s=await j(r,i,a$1.texture,"Static application asset");return {data:s.data,file:s.path}}a(Vr,"staticRequestFile");async function Gr(r,e$1,t,n,i){let s=await realpath(r.root),a=await realpath(y.resolve(s,r.serve));if(!e(s,a)||a===s)throw new Error("--serve must name a built application directory inside the project root.");let d=await Ur(s,a),u=await $(),m=Hr(e$1,t),h=Se(T(r.runtime.three)),g=createServer((o,l)=>{(async()=>{if(ir(o,l,n,i,e$1!=="precompiled"))return;let f=new URL(o.url??"/","http://three-blocks.invalid");if(o.method!=="GET"&&o.method!=="HEAD"){l.statusCode=405,l.end("GET or HEAD required");return}let w=f.pathname===Xe?u:f.pathname===Ze?m:f.pathname===er?h:void 0;if(w!==void 0){l.statusCode=200,l.setHeader("Content-Type","text/javascript; charset=utf-8"),l.setHeader("Cache-Control","no-store"),l.end(o.method==="HEAD"?void 0:w);return}let R=await Vr(a,f.pathname);if(R===void 0){l.statusCode=404,l.end("Not found");return}let P=y.extname(R.file).toLowerCase(),k=P===".html"?Buffer.from(Nr(R.data.toString("utf8"))):R.data;l.statusCode=200,l.setHeader("Content-Type",Fr[P]??"application/octet-stream"),l.setHeader("Content-Length",String(k.byteLength)),l.setHeader("Cache-Control","no-store"),l.end(o.method==="HEAD"?void 0:k);})().catch(f=>{if(l.headersSent)return l.destroy(f instanceof Error?f:void 0);l.statusCode=500,l.end(f instanceof Error?f.message:String(f));});});await new Promise((o,l)=>{g.once("error",l),g.listen(0,"127.0.0.1",()=>{g.off("error",l),o();});});let p=g.address();if(!p||typeof p=="string")throw new Error("Static capture server did not expose an ephemeral TCP address.");return {server:g,baseUrl:`http://127.0.0.1:${p.port}`,transform:d}}a(Gr,"startStaticShaderServer");function Wr(r,e,t){return r===e?true:t&&r!==void 0&&r!=="capture"&&e!=="capture"}a(Wr,"canReuseShaderBrowserSession");function Ye(r){let e=r instanceof Error?r.message:String(r);return e.includes("Execution context was destroyed")&&e.includes("navigation")}a(Ye,"isRetryableShaderObservationNavigation");var K=class{static{a(this,"PlaywrightShaderDriver");}#e;#r=new ye;#n=new ge;#l;#p;#s;#a;#t;#i;#m;#d;#h;#c=0;#u;constructor(e){this.#e=e;}#o(){return this.#l?.status??this.#p??{seen:false,applied:false,alreadyPresent:false}}async#f(e){if(this.#t?.isConnected()===true)return;this.#t=void 0;let t=await Ar();this.#u??=await mkdtemp(y.join(tmpdir(),"three-blocks-shader-cache-")),this.#t=await t.launch({headless:c(this.#e.headed===true),args:[...b(),`--disk-cache-dir=${this.#u}`],timeout:e.timeoutMs}),this.#c=0;}async#y(e,t){let n=this.#s!==void 0||this.#a!==void 0||this.#e.url!==void 0&&this.#i!==void 0,i=this.#a!==void 0?this.#d===e:Wr(this.#d,e,t.bridge.legacyLab);if(n&&i){this.#d=e,await this.#f(t);return}if(n&&await this.close(),this.#d=e,this.#e.url!==void 0){let s=new URL(this.#e.url);if(!["http:","https:"].includes(s.protocol)||s.username||s.password||s.hash)throw new Error("Attached shader URL must be an HTTP(S) URL without credentials or a fragment.");this.#i=s.href,this.#p={seen:true,applied:true,alreadyPresent:false,captureApplied:true,id:"attached-application"},await this.#f(t);return}if(this.#e.serve!==void 0)try{let s=await Gr({root:this.#e.root,runtime:this.#e.runtime,serve:this.#e.serve,...this.#e.headed===void 0?{}:{headed:this.#e.headed}},e,t,this.#r,this.#n);this.#a=s.server,this.#p=s.transform,this.#i=s.baseUrl,await this.#f(t);return}catch(s){throw await this.close(),s}this.#l=Ve(this.#e.runtime.three,{disableTimestampQueries:_.env.THREE_BLOCKS_SOFTWARE_WEBGPU==="1",...t.bridge.legacyLab?{}:{capture:{capture:e==="capture",forceLive:e!=="precompiled",settleFrames:t.settleFrames,settleTimeoutMs:t.settleTimeoutMs??3e4,readiness:t.readiness}}}),this.#m={THREE_BLOCKS_SHADER_TOOL:_.env.THREE_BLOCKS_SHADER_TOOL,THREE_BLOCKS_PRECOMPILE_CAPTURE_SERVER:_.env.THREE_BLOCKS_PRECOMPILE_CAPTURE_SERVER},_.env.THREE_BLOCKS_SHADER_TOOL="1",_.env.THREE_BLOCKS_PRECOMPILE_CAPTURE_SERVER="1";try{let s=await jr(this.#e.root);this.#s=await s({root:this.#e.root,logLevel:"error",plugins:[this.#l.plugin,Lr(this.#r,this.#n,e!=="precompiled",T(this.#e.runtime.three))],server:{host:"127.0.0.1",port:0}}),await this.#s.listen();let a=this.#s.httpServer?.address();if(!a||typeof a=="string")throw new Error("Vite did not expose an ephemeral TCP address.");this.#i=`http://127.0.0.1:${a.port}`,await this.#f(t);}catch(s){throw await this.close(),s}}async capture(e,t){let n=Date.now();if(await this.#y("capture",t),!this.#t||!this.#i)throw new Error("Shader browser driver did not start.");let i=this.#t,s=await i.newContext({viewport:t.viewport});this.#e.url!==void 0&&await he(s,this.#r,this.#n,"capture",t,T(this.#e.runtime.three));let a$1=await s.newPage(),d=me(a$1);this.#n.clear(e.key);let u=this.#r.wait(e.key,t.timeoutMs),m=Promise.race([u,d.first.then(o=>Promise.reject(o))]),h=a(()=>{},"resolveDisconnected"),g=new Promise(o=>{h=o;}),p=a(()=>h(new Error("Shader capture browser disconnected before posting a manifest.")),"onDisconnected");i.on("disconnected",p);try{let o=a$1.goto(We(this.#i,e,{threeBlocksShaderCapture:"1",capture:"1",captureId:e.key,captureFrames:String(Math.max(4,t.settleFrames)),settleFrames:String(t.settleFrames)}),{waitUntil:"domcontentloaded",timeout:t.timeoutMs}),l=await Or(o,Promise.race([m,g.then(w=>Promise.reject(w))]));pe(this.#o());let f=[...d.page,...d.console];if(f.length>0)throw new Error(`Capture browser errors:
91
- - ${f.join(`
92
- - `)}`);return a$2(l)?{...l,timing:{...a$2(l.timing)?l.timing:{},launch:n,...this.#n.firstRequest(e.key)===void 0?{}:{firstRequest:this.#n.firstRequest(e.key)},posted:Date.now()}}:l}catch(o){let l=o instanceof Error?o:new Error(String(o));this.#r.cancel(e.key,l),await u.catch(()=>{});let f=this.#n.read(e.key);if(l.message.includes("timed out")){let w=await Ke(()=>a$1.evaluate(()=>{let R=globalThis,P=R.__threeBlocksShaderTools,k=P&&typeof P=="object"?P:void 0,J=R.document,C=Reflect.get(R,Symbol.for("three-blocks.shader-capture.cache-value.v1")),E=R.location,F=E!==null&&typeof E=="object"&&typeof Reflect.get(E,"href")=="string"?String(Reflect.get(E,"href")):"http://three-blocks.invalid/",N=new URL(F).searchParams.get("captureId")??"default",z=C!==null&&typeof C=="object"&&typeof Reflect.get(C,"registrations")=="function"?Reflect.apply(Reflect.get(C,"registrations"),C,[N]):void 0;return {documentReadyState:J?.readyState??null,parityTargetFrame:Number(R.__threeBlocksParityTargetFrame??0),parityCompletedFrame:Number(R.__threeBlocksParityCompletedFrame??0),readiness:k?.readiness??null,captureCache:C!==null&&typeof C=="object"?{activeScene:Reflect.get(C,"activeScene")??null,registrations:Array.isArray(z)?z.slice(0,16).map(M=>M!==null&&typeof M=="object"?{key:Reflect.get(M,"key")??null,kind:Reflect.get(M,"kind")??null}:null):null}:null,threeRuntimeResources:performance.getEntriesByType("resource").map(M=>M.name).filter(M=>M.includes("three.webgpu"))}}));throw new Error(`${l.message} Last capture state for "${e.key}": ${JSON.stringify({page:w,telemetry:f??null,transform:this.#o()})}`)}throw l}finally{i.off("disconnected",p),await L(()=>s.close()),this.#c++,(!i.isConnected()||this.#c>=(t.browserRelaunchScenes??8))&&(this.#t===i&&(this.#t=void 0),await L(()=>i.close()),this.#c=0);}}async observe(e,t,n,i){for(let s=0;s<2;s++)try{return await this.#g(e,t,n,i)}catch(a){if(s===0&&Ye(a))continue;throw a}throw new Error(`Shader observation retry was exhausted for scene "${e.key}".`)}async#g(e,t,n,i){if(await this.#y(t,n),!this.#t||!this.#i)throw new Error("Shader browser driver did not start.");let s=await this.#t.newContext({viewport:n.viewport});this.#e.url!==void 0&&await he(s,this.#r,this.#n,t,n,T(this.#e.runtime.three));let a=await s.newPage(),d=me(a);this.#n.clear(e.key);try{await a.goto(We(this.#i,e,{threeBlocksShaderCapture:"1",threeBlocksShaderMode:t,captureId:e.key,...t==="live"?{precompiled:"0"}:{}}),{waitUntil:"domcontentloaded",timeout:n.timeoutMs}),await Promise.race([a.waitForFunction(n.bridge.legacyLab?"globalThis.__threeBlocks?.compileEnd === true":"globalThis.__threeBlocksShaderTools?.readiness?.compileEnd === true",void 0,{timeout:n.timeoutMs}),d.first.then(o=>Promise.reject(o))]),ee(await re(a,n.bridge.legacyLab),e,n.bridge.legacyLab,this.#o(),T(this.#e.runtime.three)),await Je(a,n,d),await Promise.race([a.waitForFunction(n.bridge.legacyLab?"true":"globalThis.__threeBlocksShaderTools?.readiness?.firstFrame === true",void 0,{timeout:n.timeoutMs}),d.first.then(o=>Promise.reject(o))]),await q(a,n,1);let u=Buffer.from(await a.screenshot({type:"png"})),m=e.parityFrames??n.parity.frames,h=await q(a,n,m,i),g=Buffer.from(await a.screenshot({type:"png"}));e.parityFrames!==void 0&&m<n.parity.frames&&await q(a,n,n.parity.frames-m);let p=ee(await re(a,n.bridge.legacyLab),e,n.bridge.legacyLab,this.#o(),T(this.#e.runtime.three));return this.#h===void 0&&(this.#h=await a.evaluate(async()=>{let o=Reflect.get(navigator,"gpu"),l=typeof o=="object"&&o!==null?Reflect.get(o,"requestAdapter"):void 0,f=typeof l=="function"?await Reflect.apply(l,o,[]):void 0,w=typeof f=="object"&&f!==null?Reflect.get(f,"info"):void 0,R=["description","device","architecture","vendor"].flatMap(P=>{let k=typeof w=="object"&&w!==null?Reflect.get(w,P):void 0;return typeof k=="string"&&k.length>0?[k]:[]});return {adapter:[...new Set(R)].join(" \xB7 ")||"WebGPU adapter",platform:navigator.platform||navigator.userAgent}})),{scene:e.key,mode:t,...p,frame:h,firstFrameScreenshot:u,screenshot:g,errors:[...d.page,...d.console]}}catch(u){let m=u instanceof Error?u:new Error(String(u));if(/(?:timed?\s*out|timeout)/iu.test(m.message)){let h=this.#n.read(e.key),g=await Ke(()=>a.evaluate(()=>{let p=globalThis,o=p.__threeBlocksShaderTools,l=o&&typeof o=="object"?o:void 0;return {documentReadyState:p.document?.readyState??null,parityTargetFrame:Number(p.__threeBlocksParityTargetFrame??0),parityCompletedFrame:Number(p.__threeBlocksParityCompletedFrame??0),readiness:l?.readiness??null,threeRuntimeResources:performance.getEntriesByType("resource").map(w=>w.name).filter(w=>w.includes("three.webgpu"))}}));throw new Error(`${m.message} Last ${t} state for "${e.key}": ${JSON.stringify({page:g,telemetry:h??null})}`)}throw m}finally{await L(()=>s.close());}}async observePublished(e,t){for(let n=0;n<2;n++)try{return await this.#S(e,t)}catch(i){if(n===0&&Ye(i))continue;throw i}throw new Error(`Published shader observation retry was exhausted for scene "${e.key}".`)}async#S(e,t){if(await this.#y("precompiled",t),!this.#t||!this.#i)throw new Error("Shader browser driver did not start.");let n=await this.#t.newContext({viewport:t.viewport});this.#e.url!==void 0&&await he(n,this.#r,this.#n,"precompiled",t,T(this.#e.runtime.three));let i=await n.newPage(),s=me(i);this.#n.clear(e.key);try{await i.goto(Dr(this.#i,e),{waitUntil:"domcontentloaded",timeout:t.timeoutMs}),await Promise.race([i.waitForFunction(t.bridge.legacyLab?"globalThis.__threeBlocks?.compileEnd === true":"globalThis.__threeBlocksShaderTools?.readiness?.compileEnd === true",void 0,{timeout:t.timeoutMs}),s.first.then(h=>Promise.reject(h))]),await Je(i,t,s),ee(await re(i,t.bridge.legacyLab),e,t.bridge.legacyLab,this.#o(),T(this.#e.runtime.three)),await q(i,t,2);let a=await ze(i),d=await q(i,t,120),u=await ze(i),m=ee(await re(i,t.bridge.legacyLab),e,t.bridge.legacyLab,this.#o(),T(this.#e.runtime.three));return {scene:e.key,mode:"precompiled",...m,frame:d,firstFrameScreenshot:a,beforeScreenshot:a,screenshot:u,errors:[...s.page,...s.console]}}finally{await L(()=>n.close());}}timingEnvironment(){return this.#h??{adapter:"WebGPU adapter",platform:`${_.platform}/${_.arch}`}}async close(){this.#r.rejectAll(new Error("Shader browser driver closed.")),this.#t&&await L(()=>this.#t?.close()??Promise.resolve());let e=this.#s?.httpServer,t=e?Reflect.get(e,"closeAllConnections"):void 0;if(e&&typeof t=="function"&&Reflect.apply(t,e,[]),this.#s&&await L(()=>this.#s?.close()??Promise.resolve()),this.#a){let n=this.#a;n.closeAllConnections(),await L(()=>new Promise(i=>{n.close(()=>i());}));}if(this.#t=void 0,this.#s=void 0,this.#a=void 0,this.#i=void 0,this.#l=void 0,this.#p=void 0,this.#d=void 0,this.#h=void 0,this.#c=0,this.#u!==void 0&&(await rm(this.#u,{recursive:true,force:true}),this.#u=void 0),this.#m){for(let[n,i]of Object.entries(this.#m))i===void 0?delete _.env[n]:_.env[n]=i;this.#m=void 0;}}};function Ut(r){return new K(r)}a(Ut,"createPlaywrightShaderDriver");function Vt(r){return new K(r)}a(Vt,"createStaticPlaywrightShaderDriver");function Gt(r){return new K(r)}a(Gt,"createAttachedPlaywrightShaderDriver");
93
- export{T as a,O as b,it as c,B as d,st as e,at as f,ot as g,dt as h,ct as i,ut as j,Or as k,Ir as l,Se as m,Wr as n,Ye as o,Ut as p,Vt as q,Gt as r};