@drawcall/lod 0.2.0 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (355) hide show
  1. package/README.md +6 -7
  2. package/dist/bake.d.ts +36 -0
  3. package/dist/bake.js +176 -0
  4. package/dist/bake.js.map +1 -0
  5. package/dist/baked/codec.d.ts +3 -6
  6. package/dist/baked/codec.js +48 -154
  7. package/dist/baked/codec.js.map +1 -1
  8. package/dist/baked/coverage.d.ts +6 -3
  9. package/dist/baked/coverage.js +6 -3
  10. package/dist/baked/coverage.js.map +1 -1
  11. package/dist/baked/fields.d.ts +9 -0
  12. package/dist/baked/fields.js +22 -0
  13. package/dist/baked/fields.js.map +1 -0
  14. package/dist/baked/index.d.ts +14 -8
  15. package/dist/baked/index.js +24 -22
  16. package/dist/baked/index.js.map +1 -1
  17. package/dist/baked/interior/faces.d.ts +4 -3
  18. package/dist/baked/interior/faces.js +16 -11
  19. package/dist/baked/interior/faces.js.map +1 -1
  20. package/dist/baked/interior/material.d.ts +7 -10
  21. package/dist/baked/interior/material.js +29 -36
  22. package/dist/baked/interior/material.js.map +1 -1
  23. package/dist/baked/interior/rooms.d.ts +1 -1
  24. package/dist/baked/interior/rooms.js +2 -2
  25. package/dist/baked/interior/rooms.js.map +1 -1
  26. package/dist/baked/low.js +5 -4
  27. package/dist/baked/low.js.map +1 -1
  28. package/dist/baked/raster.js +6 -6
  29. package/dist/baked/raster.js.map +1 -1
  30. package/dist/baked/textures.d.ts +17 -0
  31. package/dist/baked/textures.js +95 -0
  32. package/dist/baked/textures.js.map +1 -0
  33. package/dist/baked/transfer.js +19 -18
  34. package/dist/baked/transfer.js.map +1 -1
  35. package/dist/baked/unwrap.js +4 -3
  36. package/dist/baked/unwrap.js.map +1 -1
  37. package/dist/baked/xatlas.js.map +1 -1
  38. package/dist/codec/container.d.ts +8 -0
  39. package/dist/codec/container.js +63 -0
  40. package/dist/codec/container.js.map +1 -0
  41. package/dist/codec/mesh.d.ts +8 -0
  42. package/dist/{mesh/codec.js → codec/mesh.js} +80 -52
  43. package/dist/codec/mesh.js.map +1 -0
  44. package/dist/dispose.d.ts +8 -5
  45. package/dist/dispose.js +22 -24
  46. package/dist/dispose.js.map +1 -1
  47. package/dist/foliage.d.ts +32 -0
  48. package/dist/foliage.js +137 -0
  49. package/dist/foliage.js.map +1 -0
  50. package/dist/impostor/bake/atlas.d.ts +4 -4
  51. package/dist/impostor/bake/atlas.js +12 -12
  52. package/dist/impostor/bake/atlas.js.map +1 -1
  53. package/dist/impostor/bake/fit.d.ts +8 -0
  54. package/dist/impostor/bake/fit.js +28 -0
  55. package/dist/impostor/bake/fit.js.map +1 -0
  56. package/dist/impostor/bake/index.d.ts +22 -14
  57. package/dist/impostor/bake/index.js +50 -134
  58. package/dist/impostor/bake/index.js.map +1 -1
  59. package/dist/impostor/bake/materials.d.ts +3 -3
  60. package/dist/impostor/bake/materials.js +51 -13
  61. package/dist/impostor/bake/materials.js.map +1 -1
  62. package/dist/impostor/bake/sheet.d.ts +8 -0
  63. package/dist/impostor/bake/sheet.js +90 -0
  64. package/dist/impostor/bake/sheet.js.map +1 -0
  65. package/dist/impostor/bake/source.d.ts +3 -2
  66. package/dist/impostor/bake/source.js +9 -20
  67. package/dist/impostor/bake/source.js.map +1 -1
  68. package/dist/impostor/codec.d.ts +4 -5
  69. package/dist/impostor/codec.js +36 -109
  70. package/dist/impostor/codec.js.map +1 -1
  71. package/dist/impostor/impostor.d.ts +31 -7
  72. package/dist/impostor/impostor.js +21 -6
  73. package/dist/impostor/impostor.js.map +1 -1
  74. package/dist/impostor/ktx2/encode.d.ts +26 -0
  75. package/dist/impostor/ktx2/encode.js +120 -0
  76. package/dist/impostor/ktx2/encode.js.map +1 -0
  77. package/dist/impostor/ktx2/transcode.d.ts +3 -0
  78. package/dist/impostor/ktx2/transcode.js +99 -0
  79. package/dist/impostor/ktx2/transcode.js.map +1 -0
  80. package/dist/impostor/ktx2/uastc.d.ts +7 -0
  81. package/dist/impostor/ktx2/uastc.js +65 -0
  82. package/dist/impostor/ktx2/uastc.js.map +1 -0
  83. package/dist/impostor/ktx2/wasm/encoder.d.ts +4 -0
  84. package/dist/impostor/ktx2/wasm/encoder.js +10 -0
  85. package/dist/impostor/ktx2/wasm/encoder.js.map +1 -0
  86. package/dist/impostor/ktx2/wasm/transcoder.d.ts +3 -0
  87. package/dist/impostor/ktx2/wasm/transcoder.js +9 -0
  88. package/dist/impostor/ktx2/wasm/transcoder.js.map +1 -0
  89. package/dist/impostor/ktx2/worker.d.ts +1 -0
  90. package/dist/impostor/ktx2/worker.js +10 -0
  91. package/dist/impostor/ktx2/worker.js.map +1 -0
  92. package/dist/impostor/mesh/card.d.ts +4 -4
  93. package/dist/impostor/mesh/card.js +7 -7
  94. package/dist/impostor/mesh/card.js.map +1 -1
  95. package/dist/impostor/mesh/index.d.ts +7 -6
  96. package/dist/impostor/mesh/index.js +10 -11
  97. package/dist/impostor/mesh/index.js.map +1 -1
  98. package/dist/impostor/mesh/material.d.ts +18 -9
  99. package/dist/impostor/mesh/material.js +40 -27
  100. package/dist/impostor/mesh/material.js.map +1 -1
  101. package/dist/impostor/mesh/surface.d.ts +1 -1
  102. package/dist/impostor/mesh/surface.js +13 -9
  103. package/dist/impostor/mesh/surface.js.map +1 -1
  104. package/dist/impostor/mesh/textures.d.ts +3 -3
  105. package/dist/impostor/mesh/textures.js +24 -34
  106. package/dist/impostor/mesh/textures.js.map +1 -1
  107. package/dist/index.d.ts +13 -11
  108. package/dist/index.js +12 -10
  109. package/dist/index.js.map +1 -1
  110. package/dist/instanced/camera.d.ts +34 -0
  111. package/dist/instanced/camera.js +45 -0
  112. package/dist/instanced/camera.js.map +1 -0
  113. package/dist/instanced/clusters.d.ts +54 -0
  114. package/dist/instanced/clusters.js +151 -0
  115. package/dist/instanced/clusters.js.map +1 -0
  116. package/dist/instanced/cull.d.ts +28 -0
  117. package/dist/instanced/cull.js +22 -0
  118. package/dist/instanced/cull.js.map +1 -0
  119. package/dist/instanced/instances.d.ts +39 -0
  120. package/dist/instanced/instances.js +104 -0
  121. package/dist/instanced/instances.js.map +1 -0
  122. package/dist/instanced/key.d.ts +19 -0
  123. package/dist/instanced/key.js +45 -0
  124. package/dist/instanced/key.js.map +1 -0
  125. package/dist/instanced/levels.d.ts +60 -0
  126. package/dist/instanced/levels.js +131 -0
  127. package/dist/instanced/levels.js.map +1 -0
  128. package/dist/instanced/lists.d.ts +57 -0
  129. package/dist/instanced/lists.js +114 -0
  130. package/dist/instanced/lists.js.map +1 -0
  131. package/dist/instanced/measure.d.ts +28 -0
  132. package/dist/instanced/measure.js +203 -0
  133. package/dist/instanced/measure.js.map +1 -0
  134. package/dist/instanced/meshes.d.ts +44 -51
  135. package/dist/instanced/meshes.js +167 -179
  136. package/dist/instanced/meshes.js.map +1 -1
  137. package/dist/instanced/mirror.d.ts +24 -0
  138. package/dist/instanced/mirror.js +76 -0
  139. package/dist/instanced/mirror.js.map +1 -0
  140. package/dist/instanced/raycast.d.ts +10 -11
  141. package/dist/instanced/raycast.js +31 -41
  142. package/dist/instanced/raycast.js.map +1 -1
  143. package/dist/instanced/rows.d.ts +50 -0
  144. package/dist/instanced/rows.js +36 -0
  145. package/dist/instanced/rows.js.map +1 -0
  146. package/dist/instanced/shape.d.ts +27 -0
  147. package/dist/instanced/shape.js +54 -0
  148. package/dist/instanced/shape.js.map +1 -0
  149. package/dist/instanced/sort.d.ts +61 -0
  150. package/dist/instanced/sort.js +192 -0
  151. package/dist/instanced/sort.js.map +1 -0
  152. package/dist/instanced/update.d.ts +34 -0
  153. package/dist/instanced/update.js +180 -0
  154. package/dist/instanced/update.js.map +1 -0
  155. package/dist/levels/bounds.d.ts +21 -0
  156. package/dist/levels/bounds.js +42 -0
  157. package/dist/levels/bounds.js.map +1 -0
  158. package/dist/levels/cameras.d.ts +48 -0
  159. package/dist/levels/cameras.js +122 -0
  160. package/dist/levels/cameras.js.map +1 -0
  161. package/dist/levels/compile/contexts.d.ts +30 -0
  162. package/dist/levels/compile/contexts.js +18 -0
  163. package/dist/levels/compile/contexts.js.map +1 -0
  164. package/dist/levels/compile/index.d.ts +41 -0
  165. package/dist/levels/compile/index.js +193 -0
  166. package/dist/levels/compile/index.js.map +1 -0
  167. package/dist/levels/compile/pipelines.d.ts +26 -0
  168. package/dist/levels/compile/pipelines.js +172 -0
  169. package/dist/levels/compile/pipelines.js.map +1 -0
  170. package/dist/levels/compiles.d.ts +29 -0
  171. package/dist/levels/compiles.js +50 -0
  172. package/dist/levels/compiles.js.map +1 -0
  173. package/dist/levels/draw.d.ts +102 -0
  174. package/dist/levels/draw.js +401 -0
  175. package/dist/levels/draw.js.map +1 -0
  176. package/dist/levels/fade.d.ts +60 -0
  177. package/dist/levels/fade.js +129 -0
  178. package/dist/levels/fade.js.map +1 -0
  179. package/dist/levels/index.d.ts +99 -0
  180. package/dist/levels/index.js +155 -0
  181. package/dist/levels/index.js.map +1 -0
  182. package/dist/levels/item.d.ts +38 -0
  183. package/dist/levels/item.js +89 -0
  184. package/dist/levels/item.js.map +1 -0
  185. package/dist/levels/load.d.ts +31 -0
  186. package/dist/levels/load.js +144 -0
  187. package/dist/levels/load.js.map +1 -0
  188. package/dist/levels/manager.d.ts +158 -0
  189. package/dist/levels/manager.js +352 -0
  190. package/dist/levels/manager.js.map +1 -0
  191. package/dist/{material.d.ts → levels/material.d.ts} +2 -2
  192. package/dist/{material.js → levels/material.js} +6 -5
  193. package/dist/levels/material.js.map +1 -0
  194. package/dist/levels/renderer.d.ts +32 -0
  195. package/dist/levels/renderer.js +57 -0
  196. package/dist/levels/renderer.js.map +1 -0
  197. package/dist/levels/requests.d.ts +52 -0
  198. package/dist/levels/requests.js +97 -0
  199. package/dist/levels/requests.js.map +1 -0
  200. package/dist/levels/screen.d.ts +14 -0
  201. package/dist/levels/screen.js +21 -0
  202. package/dist/levels/screen.js.map +1 -0
  203. package/dist/loader/build.d.ts +10 -0
  204. package/dist/loader/build.js +28 -0
  205. package/dist/loader/build.js.map +1 -0
  206. package/dist/loader/context.d.ts +44 -0
  207. package/dist/loader/context.js +96 -0
  208. package/dist/loader/context.js.map +1 -0
  209. package/dist/loader/entry.d.ts +4 -0
  210. package/dist/loader/entry.js +43 -0
  211. package/dist/loader/entry.js.map +1 -0
  212. package/dist/loader/index.d.ts +76 -0
  213. package/dist/loader/index.js +272 -0
  214. package/dist/loader/index.js.map +1 -0
  215. package/dist/loader/level.d.ts +41 -0
  216. package/dist/loader/level.js +140 -0
  217. package/dist/loader/level.js.map +1 -0
  218. package/dist/loader/node.d.ts +26 -0
  219. package/dist/loader/node.js +199 -0
  220. package/dist/loader/node.js.map +1 -0
  221. package/dist/loader/request.d.ts +54 -0
  222. package/dist/loader/request.js +19 -0
  223. package/dist/loader/request.js.map +1 -0
  224. package/dist/loader/url.d.ts +10 -6
  225. package/dist/loader/url.js +22 -14
  226. package/dist/loader/url.js.map +1 -1
  227. package/dist/lod.d.ts +144 -43
  228. package/dist/lod.js +354 -163
  229. package/dist/lod.js.map +1 -1
  230. package/dist/meshopt.d.ts +6 -0
  231. package/dist/meshopt.js +20 -0
  232. package/dist/meshopt.js.map +1 -0
  233. package/dist/node-process.d.ts +5 -0
  234. package/dist/node-process.js +6 -0
  235. package/dist/node-process.js.map +1 -0
  236. package/dist/node.d.ts +2 -0
  237. package/dist/node.js +5 -0
  238. package/dist/node.js.map +1 -0
  239. package/dist/simplify/cards.d.ts +14 -0
  240. package/dist/simplify/cards.js +128 -0
  241. package/dist/simplify/cards.js.map +1 -0
  242. package/dist/{simplify.d.ts → simplify/index.d.ts} +8 -5
  243. package/dist/{simplify.js → simplify/index.js} +45 -27
  244. package/dist/simplify/index.js.map +1 -0
  245. package/dist/{bounds.d.ts → source/detail.d.ts} +9 -23
  246. package/dist/{bounds.js → source/detail.js} +28 -58
  247. package/dist/source/detail.js.map +1 -0
  248. package/dist/source/deviation.js +6 -6
  249. package/dist/source/deviation.js.map +1 -1
  250. package/dist/source/{shading.d.ts → evaluator.d.ts} +10 -10
  251. package/dist/source/{shading.js → evaluator.js} +5 -5
  252. package/dist/source/evaluator.js.map +1 -0
  253. package/dist/source/{trace.d.ts → raycaster.d.ts} +6 -6
  254. package/dist/source/{trace.js → raycaster.js} +8 -8
  255. package/dist/source/raycaster.js.map +1 -0
  256. package/dist/source/{texels.d.ts → sampler.d.ts} +1 -1
  257. package/dist/source/{texels.js → sampler.js} +8 -5
  258. package/dist/source/sampler.js.map +1 -0
  259. package/dist/source/source.d.ts +1 -1
  260. package/dist/source/source.js +1 -1
  261. package/dist/source/source.js.map +1 -1
  262. package/dist/source/surface.js +1 -1
  263. package/dist/source/surface.js.map +1 -1
  264. package/dist/task.d.ts +6 -0
  265. package/dist/{pause.js → task.js} +5 -5
  266. package/dist/task.js.map +1 -0
  267. package/dist/three.d.ts +19 -30
  268. package/dist/three.js +30 -57
  269. package/dist/three.js.map +1 -1
  270. package/dist/tsl.d.ts +8 -12
  271. package/dist/tsl.js +11 -39
  272. package/dist/tsl.js.map +1 -1
  273. package/dist/typegpu.d.ts +37 -0
  274. package/dist/typegpu.js +37 -0
  275. package/dist/typegpu.js.map +1 -0
  276. package/dist/wind/bounds.js +3 -3
  277. package/dist/wind/bounds.js.map +1 -1
  278. package/dist/wind/hooks.d.ts +7 -4
  279. package/dist/wind/hooks.js +5 -2
  280. package/dist/wind/hooks.js.map +1 -1
  281. package/dist/wind/index.d.ts +4 -4
  282. package/dist/wind/index.js +25 -23
  283. package/dist/wind/index.js.map +1 -1
  284. package/dist/wind/sway.d.ts +2 -0
  285. package/dist/wind/sway.js +4 -1
  286. package/dist/wind/sway.js.map +1 -1
  287. package/package.json +24 -10
  288. package/skills/lod/SKILL.md +120 -32
  289. package/dist/bounds.js.map +0 -1
  290. package/dist/compile.d.ts +0 -4
  291. package/dist/compile.js +0 -100
  292. package/dist/compile.js.map +0 -1
  293. package/dist/deferred.d.ts +0 -12
  294. package/dist/deferred.js +0 -27
  295. package/dist/deferred.js.map +0 -1
  296. package/dist/fade.d.ts +0 -36
  297. package/dist/fade.js +0 -112
  298. package/dist/fade.js.map +0 -1
  299. package/dist/instanced/args.d.ts +0 -20
  300. package/dist/instanced/args.js +0 -77
  301. package/dist/instanced/args.js.map +0 -1
  302. package/dist/instanced/blocks.d.ts +0 -66
  303. package/dist/instanced/blocks.js +0 -294
  304. package/dist/instanced/blocks.js.map +0 -1
  305. package/dist/instanced/dirty.d.ts +0 -15
  306. package/dist/instanced/dirty.js +0 -96
  307. package/dist/instanced/dirty.js.map +0 -1
  308. package/dist/instanced/index.d.ts +0 -90
  309. package/dist/instanced/index.js +0 -349
  310. package/dist/instanced/index.js.map +0 -1
  311. package/dist/instanced/parts.d.ts +0 -14
  312. package/dist/instanced/parts.js +0 -79
  313. package/dist/instanced/parts.js.map +0 -1
  314. package/dist/instanced/select.d.ts +0 -92
  315. package/dist/instanced/select.js +0 -315
  316. package/dist/instanced/select.js.map +0 -1
  317. package/dist/instanced/store.d.ts +0 -31
  318. package/dist/instanced/store.js +0 -96
  319. package/dist/instanced/store.js.map +0 -1
  320. package/dist/levels.d.ts +0 -95
  321. package/dist/levels.js +0 -171
  322. package/dist/levels.js.map +0 -1
  323. package/dist/loader/bundle.d.ts +0 -25
  324. package/dist/loader/bundle.js +0 -241
  325. package/dist/loader/bundle.js.map +0 -1
  326. package/dist/loader/cache.d.ts +0 -15
  327. package/dist/loader/cache.js +0 -75
  328. package/dist/loader/cache.js.map +0 -1
  329. package/dist/loader/provenance.d.ts +0 -30
  330. package/dist/loader/provenance.js +0 -105
  331. package/dist/loader/provenance.js.map +0 -1
  332. package/dist/loader.d.ts +0 -55
  333. package/dist/loader.js +0 -239
  334. package/dist/loader.js.map +0 -1
  335. package/dist/material.js.map +0 -1
  336. package/dist/mesh/codec.d.ts +0 -4
  337. package/dist/mesh/codec.js.map +0 -1
  338. package/dist/pause.d.ts +0 -6
  339. package/dist/pause.js.map +0 -1
  340. package/dist/queue.d.ts +0 -2
  341. package/dist/queue.js +0 -33
  342. package/dist/queue.js.map +0 -1
  343. package/dist/renderer.d.ts +0 -21
  344. package/dist/renderer.js +0 -83
  345. package/dist/renderer.js.map +0 -1
  346. package/dist/residency.d.ts +0 -44
  347. package/dist/residency.js +0 -205
  348. package/dist/residency.js.map +0 -1
  349. package/dist/simplify.js.map +0 -1
  350. package/dist/source/shading.js.map +0 -1
  351. package/dist/source/texels.js.map +0 -1
  352. package/dist/source/trace.js.map +0 -1
  353. package/dist/view.d.ts +0 -45
  354. package/dist/view.js +0 -131
  355. package/dist/view.js.map +0 -1
@@ -0,0 +1,193 @@
1
+ import { isMesh, isNode, isTexture } from "../../three.js";
2
+ import { compileMesh, frame, sharePipelines } from "./pipelines.js";
3
+ const compilers = new WeakMap();
4
+ /** What `renderer` prepares levels with: one Compiler per renderer, made the first time a level compiles for it. */
5
+ export function compilerOf(renderer) {
6
+ let compiler = compilers.get(renderer);
7
+ if (!compiler)
8
+ compilers.set(renderer, (compiler = new Compiler(renderer)));
9
+ return compiler;
10
+ }
11
+ /**
12
+ * What a renderer prepares for the levels arriving: the levels share its queue's budget and its pipeline cache, which
13
+ * it shares the readiness of (see `sharePipelines`).
14
+ */
15
+ export class Compiler {
16
+ renderer;
17
+ /** Uploaded since the last frame. */
18
+ uploaded = 0;
19
+ /** The last upload: uploads run in turn. */
20
+ uploads = Promise.resolve();
21
+ /**
22
+ * The last draw compiled for each shader build: material, attributes, target, shadow map and nesting. three starts a
23
+ * build for each draw that misses its cache, even one another draw is building, so a draw that builds alike waits
24
+ * for the last one and finds its build cached.
25
+ */
26
+ builds = new Map();
27
+ constructor(renderer) {
28
+ this.renderer = renderer;
29
+ sharePipelines(renderer);
30
+ }
31
+ /**
32
+ * Prepare the same target and MRT as the camera's draw, even if normal rendering has since restored the canvas, and
33
+ * the shadow maps of `compileFor`, for each mesh that casts. r186 uploads a texture synchronously inside initTexture,
34
+ * and creates a pipeline it meets while rendering synchronously, so each texture and draw is prepared here first.
35
+ * Textures upload paced across frames (see `paced`); every draw then compiles at once, as do the draws of every
36
+ * other level the renderer prepares, so their pipelines are created side by side.
37
+ */
38
+ async compileAsync(object, context, { shadows, isDisposed }) {
39
+ const { renderer } = this;
40
+ const { memory } = renderer.info;
41
+ for (const texture of textures(object))
42
+ await this.paced(() => {
43
+ const known = memory.textures;
44
+ renderer.initTexture(texture);
45
+ return memory.textures === known ? 0 : bytesOf(texture);
46
+ });
47
+ const meshes = [];
48
+ object.traverse((node) => {
49
+ if (isMesh(node))
50
+ meshes.push(node);
51
+ });
52
+ const draws = [];
53
+ for (const mesh of meshes) {
54
+ const targets = [{ context, overrideMaterial: null }];
55
+ if (mesh.castShadow)
56
+ for (const { camera, target, overrideMaterial, depth } of shadows.filter((map) => map.scene === context.scene))
57
+ targets.push({ context: { ...context, camera, target, mrt: null, cubeFace: 0, mipLevel: 0, depth }, overrideMaterial });
58
+ // r186 starts only the first material before yielding; isolate one draw so setup sees its captured target/MRT.
59
+ const parts = Array.isArray(mesh.material) ? mesh.geometry.groups.map((group) => [group]) : [mesh.geometry.groups];
60
+ for (const target of targets)
61
+ for (const part of parts)
62
+ draws.push(this.compileDraw(mesh, target, part, isDisposed));
63
+ }
64
+ await Promise.all(draws);
65
+ }
66
+ /** Run `upload`, which answers the bytes it uploaded, after the next frame if those since the last one reached `FRAME_UPLOAD`. */
67
+ paced(upload) {
68
+ const run = this.uploads.then(async () => {
69
+ if (this.uploaded >= FRAME_UPLOAD)
70
+ await frame();
71
+ const bytes = upload();
72
+ // The next frame empties the budget, whether or not an upload waits for it.
73
+ if (bytes > 0 && this.uploaded === 0)
74
+ void frame().then(() => void (this.uploaded = 0));
75
+ this.uploaded += bytes;
76
+ });
77
+ this.uploads = run.catch(() => { });
78
+ return run;
79
+ }
80
+ /** Compile the draw of `mesh`'s groups `part` for `target`. */
81
+ compileDraw(mesh, target, part, isDisposed) {
82
+ const { builds } = this;
83
+ const material = Array.isArray(mesh.material) ? mesh.material[part[0]?.materialIndex ?? 0] : mesh.material;
84
+ const key = [
85
+ material ? material.uuid : "none",
86
+ Object.keys(mesh.geometry.attributes).sort().join(),
87
+ target.context.target ? target.context.target.texture.id : "canvas",
88
+ target.overrideMaterial ? target.overrideMaterial.uuid : "camera",
89
+ target.context.depth,
90
+ ].join(" ");
91
+ const start = () => {
92
+ // Uploads and alike builds may have taken frames: a target disposed meanwhile stays disposed.
93
+ const drawn = target.context.target;
94
+ if (drawn && isDisposed(drawn))
95
+ return Promise.resolve();
96
+ const groups = mesh.geometry.groups;
97
+ try {
98
+ mesh.geometry.groups = part;
99
+ return compileMesh(this.renderer, mesh, target);
100
+ }
101
+ finally {
102
+ mesh.geometry.groups = groups;
103
+ }
104
+ };
105
+ const alike = builds.get(key);
106
+ const own = alike ? alike.then(start) : start();
107
+ const settled = own.then(() => { }, () => { });
108
+ builds.set(key, settled);
109
+ void settled.then(() => {
110
+ if (builds.get(key) === settled)
111
+ builds.delete(key);
112
+ });
113
+ return own;
114
+ }
115
+ }
116
+ /**
117
+ * What texture uploads may add in one frame, in bytes: a 2048² RGBA texture. Uploads run on the GPU's queue before the
118
+ * frame that follows them, which waits for them all. A draw's geometry is not paced: its buffers copy in far less
119
+ * time than a texture of the same size and its mipmaps.
120
+ */
121
+ const FRAME_UPLOAD = 16 * 2 ** 20;
122
+ const sum = (values) => values.reduce((total, value) => total + value, 0);
123
+ /**
124
+ * The bytes `texture` uploads, as three 0.186.1 uploads it: its mip levels', or its image's and the mipmaps three
125
+ * generates from it. An uncompressed cube's image is its six faces, and its mip levels are those after the first, with
126
+ * six images each; a compressed cube's faces carry their own mip levels, unless it has some.
127
+ */
128
+ function bytesOf(texture) {
129
+ const levels = texture.mipmaps ?? [];
130
+ const cube = Array.isArray(texture.image);
131
+ if (levels.length > 0 && (!cube || Reflect.get(texture, "isCompressedTexture") === true))
132
+ return bytesIn(levels);
133
+ const bytes = bytesIn(texture.image) + bytesIn(levels);
134
+ return texture.generateMipmaps && levels.length === 0 ? Math.ceil((bytes * 4) / 3) : bytes;
135
+ }
136
+ /** The bytes of an image, a mip level, a cube's face or a list of them: its data's, or four per texel. */
137
+ function bytesIn(image) {
138
+ if (Array.isArray(image))
139
+ return sum(image.map(bytesIn));
140
+ if (typeof image !== "object" || image === null)
141
+ return 0;
142
+ if (isTexture(image))
143
+ return bytesIn(image.mipmaps?.length ? image.mipmaps : image.image);
144
+ const images = Reflect.get(image, "images");
145
+ if (Array.isArray(images))
146
+ return bytesIn(images);
147
+ const data = Reflect.get(image, "data");
148
+ if (ArrayBuffer.isView(data))
149
+ return data.byteLength;
150
+ const dimension = (name) => {
151
+ const value = Reflect.get(image, name);
152
+ return typeof value === "number" ? value : 1;
153
+ };
154
+ return dimension("width") * dimension("height") * dimension("depth") * 4;
155
+ }
156
+ /**
157
+ * The textures `object`'s meshes draw: their materials', those their nodes sample, and those a material keeps in plain
158
+ * objects and arrays for nodes it makes while it builds (an impostor's atlases, a baked mesh's rooms).
159
+ */
160
+ function textures(object) {
161
+ const found = new Set();
162
+ const visited = new Set();
163
+ const visit = (value) => {
164
+ if (typeof value !== "object" || value === null || visited.has(value))
165
+ return;
166
+ visited.add(value);
167
+ if (isTexture(value))
168
+ found.add(value);
169
+ else if (isNode(value)) {
170
+ visit(Reflect.get(value, "value"));
171
+ for (const child of value.getChildren())
172
+ visit(child);
173
+ }
174
+ else if (Array.isArray(value))
175
+ for (const entry of value)
176
+ visit(entry);
177
+ else if ([Object.prototype, null].includes(Object.getPrototypeOf(value)))
178
+ for (const [key, entry] of Object.entries(value))
179
+ if (key !== "userData")
180
+ visit(entry);
181
+ };
182
+ object.traverse((node) => {
183
+ if (!isMesh(node))
184
+ return;
185
+ // userData is the application's, not what a material binds.
186
+ for (const material of [node.material].flat())
187
+ for (const [key, value] of Object.entries(material))
188
+ if (key !== "userData")
189
+ visit(value);
190
+ });
191
+ return found;
192
+ }
193
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/levels/compile/index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,26 @@
1
+ import type { Material, Mesh, Renderer } from "three/webgpu";
2
+ import type { RenderContext } from "./contexts.js";
3
+ /** The next frame. */
4
+ export declare const frame: () => Promise<void>;
5
+ /**
6
+ * r186 caches a pipeline before it finishes, but a compile reusing it receives none of its promises. Share that
7
+ * pipeline's readiness, not the readiness of every earlier level: wrap r186's `_pipelines.getForRender`, as no public
8
+ * API tells when a cached pipeline is ready. Installed once per renderer, by its Compiler. The adapter
9
+ * follows the renderer's pipeline cache lifetime; pending entries disappear on success or failure and otherwise hold no
10
+ * completed pipelines.
11
+ */
12
+ export declare function sharePipelines(renderer: Renderer): void;
13
+ /** What a level's draws are compiled for: the camera's draw, or a shadow map's with the material three overrides with. */
14
+ export interface CompileTarget {
15
+ context: RenderContext;
16
+ overrideMaterial: Material | null;
17
+ }
18
+ export declare function compileMesh(renderer: Renderer, mesh: Mesh, { context, overrideMaterial }: CompileTarget): Promise<void>;
19
+ /**
20
+ * Run `compile`, which starts a compileAsync, so that it prepares draws for renders `depth` deep. Mirrors three r186
21
+ * (0.186.1): compileAsync takes its render context, as a render of its own, with the first `_renderContexts.get` of
22
+ * its synchronous start. Only that call is given `depth`; renders the compile starts meanwhile take their own. A three
23
+ * that no longer makes that call fails here rather than compiling for the wrong depth. No public API compiles for a
24
+ * depth other than 0.
25
+ */
26
+ export declare function atDepth(renderer: Renderer, depth: number, compile: () => Promise<void>): Promise<void>;
@@ -0,0 +1,172 @@
1
+ /** The next frame. */
2
+ export const frame = () => new Promise((resolve) => requestAnimationFrame(() => resolve()));
3
+ const isPipelines = (value) => typeof value === "object" && value !== null && typeof Reflect.get(value, "getForRender") === "function";
4
+ /**
5
+ * r186 caches a pipeline before it finishes, but a compile reusing it receives none of its promises. Share that
6
+ * pipeline's readiness, not the readiness of every earlier level: wrap r186's `_pipelines.getForRender`, as no public
7
+ * API tells when a cached pipeline is ready. Installed once per renderer, by its Compiler. The adapter
8
+ * follows the renderer's pipeline cache lifetime; pending entries disappear on success or failure and otherwise hold no
9
+ * completed pipelines.
10
+ */
11
+ export function sharePipelines(renderer) {
12
+ const pipelines = Reflect.get(renderer, "_pipelines");
13
+ if (!isPipelines(pipelines))
14
+ throw new Error("Lod: three's renderer keeps no render pipelines (lod mirrors r186)");
15
+ const get = pipelines.getForRender;
16
+ const pending = new WeakMap();
17
+ pipelines.getForRender = (object, promises) => {
18
+ const before = promises?.length ?? 0;
19
+ const pipeline = get.call(pipelines, object, promises);
20
+ if (!promises)
21
+ return pipeline;
22
+ if (typeof pipeline !== "object" || pipeline === null)
23
+ throw new Error("Lod: three returned no render pipeline");
24
+ let ready = pending.get(pipeline);
25
+ if (!ready) {
26
+ ready = pipelineReady(renderer, pipeline, promises.slice(before));
27
+ pending.set(pipeline, ready);
28
+ const clear = () => pending.delete(pipeline);
29
+ void ready.then(clear, clear);
30
+ }
31
+ promises.push(ready);
32
+ return pipeline;
33
+ };
34
+ }
35
+ /**
36
+ * A cached pipeline may have been started by the host before the adapter was installed: wait until the backend's data
37
+ * for it holds a pipeline or an error. r186's `_isDeviceLost` is read as no public API tells a lost device.
38
+ */
39
+ async function pipelineReady(renderer, pipeline, started) {
40
+ await Promise.all(started);
41
+ const get = Reflect.get(renderer.backend, "get");
42
+ if (typeof get !== "function")
43
+ throw new Error("Lod: three's backend keeps no pipeline data");
44
+ for (;;) {
45
+ const data = Reflect.apply(get, renderer.backend, [pipeline]);
46
+ if (typeof data !== "object" || data === null)
47
+ throw new Error("Lod: three's backend has no render pipeline data");
48
+ if (Reflect.get(data, "error") === true)
49
+ throw new Error("Lod: render pipeline compilation failed");
50
+ if (Reflect.get(renderer, "_isDeviceLost") === true)
51
+ throw new Error("Lod: device lost while compiling a render pipeline");
52
+ if (Reflect.get(data, "pipeline"))
53
+ return;
54
+ await frame();
55
+ }
56
+ }
57
+ /**
58
+ * What r186's renderObject gives an override material for one draw, and puts back once it has handed the draw on.
59
+ * This and `DRAWN` mirror three 0.186.1's Renderer.renderObject; a three that sets other keys builds shadow shaders
60
+ * in the frame again.
61
+ */
62
+ const DRAW_STATE = ["colorNode", "depthNode", "positionNode", "side", "displacementMap", "displacementScale", "displacementBias"];
63
+ /** The keys a draw adds to an override material that lacks them, in the order it adds them. */
64
+ const DRAWN = ["alphaMap", "displacementMap", "displacementScale", "displacementBias"];
65
+ /**
66
+ * A copy of the shadow map's override material for compiling one draw. r186's compileAsync builds the draw only after
67
+ * renderObject has put back the per-draw state it gave the override (the caster's shadow nodes and side), so with the
68
+ * shared material it would prepare a pipeline the shadow map never draws with. The copy holds the state of the draw.
69
+ * It is not disposed: that would release the pipeline before the shadow map draws with it.
70
+ */
71
+ function keepingDrawState(material) {
72
+ const copy = material.clone();
73
+ // The build's cache key lists a material's keys in order. clone() leaves out those three adds to its shadow material,
74
+ // its flag and those its draws set, which the copy gets in the order the shared material has them once it drew.
75
+ for (const key of [...Object.keys(material), ...DRAWN])
76
+ if (!key.startsWith("_") && !Object.hasOwn(copy, key))
77
+ Reflect.set(copy, key, Reflect.get(material, key) ?? null);
78
+ for (const key of DRAW_STATE) {
79
+ let value = Reflect.get(copy, key);
80
+ let given = false;
81
+ Object.defineProperty(copy, key, {
82
+ get: () => value,
83
+ set: (next) => {
84
+ if (given)
85
+ return;
86
+ given = true;
87
+ value = next;
88
+ },
89
+ });
90
+ }
91
+ return copy;
92
+ }
93
+ export function compileMesh(renderer, mesh, { context, overrideMaterial }) {
94
+ const { camera, scene } = context;
95
+ const target = renderer.getRenderTarget();
96
+ const mrt = renderer.getMRT();
97
+ const cubeFace = renderer.getActiveCubeFace();
98
+ const mipLevel = renderer.getActiveMipmapLevel();
99
+ const culled = mesh.frustumCulled;
100
+ const visible = mesh.visible;
101
+ const children = mesh.children;
102
+ const background = scene.background;
103
+ const backgroundNode = scene.backgroundNode;
104
+ const override = scene.overrideMaterial;
105
+ try {
106
+ renderer.setRenderTarget(context.target, context.cubeFace, context.mipLevel);
107
+ renderer.setMRT(context.mrt);
108
+ scene.overrideMaterial = overrideMaterial && keepingDrawState(overrideMaterial);
109
+ // Demanded levels can still be hidden or outside the last camera's frustum.
110
+ mesh.frustumCulled = false;
111
+ mesh.visible = true;
112
+ mesh.children = [];
113
+ // r186 compiles backgrounds first, which would postpone this mesh until after renderer state is restored.
114
+ scene.background = null;
115
+ scene.backgroundNode = null;
116
+ return atDepth(renderer, context.depth, () => renderer.compileAsync(mesh, camera, scene));
117
+ }
118
+ finally {
119
+ scene.background = background;
120
+ scene.backgroundNode = backgroundNode;
121
+ scene.overrideMaterial = override;
122
+ mesh.children = children;
123
+ mesh.frustumCulled = culled;
124
+ mesh.visible = visible;
125
+ renderer.setRenderTarget(target, cubeFace, mipLevel);
126
+ renderer.setMRT(mrt);
127
+ }
128
+ }
129
+ const isRenderContexts = (value) => typeof value === "object" && value !== null && typeof Reflect.get(value, "get") === "function";
130
+ /**
131
+ * Run `compile`, which starts a compileAsync, so that it prepares draws for renders `depth` deep. Mirrors three r186
132
+ * (0.186.1): compileAsync takes its render context, as a render of its own, with the first `_renderContexts.get` of
133
+ * its synchronous start. Only that call is given `depth`; renders the compile starts meanwhile take their own. A three
134
+ * that no longer makes that call fails here rather than compiling for the wrong depth. No public API compiles for a
135
+ * depth other than 0.
136
+ */
137
+ export function atDepth(renderer, depth, compile) {
138
+ if (depth === 0)
139
+ return compile();
140
+ const contexts = Reflect.get(renderer, "_renderContexts");
141
+ if (!isRenderContexts(contexts))
142
+ throw new Error("Lod: three's renderer keeps no render contexts");
143
+ const own = Object.hasOwn(contexts, "get");
144
+ const get = contexts.get;
145
+ let taken = false;
146
+ const restore = () => {
147
+ if (own)
148
+ contexts.get = get;
149
+ else
150
+ Reflect.deleteProperty(contexts, "get");
151
+ };
152
+ contexts.get = (target, mrt) => {
153
+ taken = true;
154
+ restore();
155
+ return get.call(contexts, target, mrt, depth);
156
+ };
157
+ let result;
158
+ try {
159
+ result = compile();
160
+ }
161
+ finally {
162
+ if (!taken)
163
+ restore();
164
+ }
165
+ // compileAsync returns at once on a lost device, which is no fault of three's version; r186's `_isDeviceLost` alone
166
+ // tells it.
167
+ if (taken || Reflect.get(renderer, "_isDeviceLost") === true)
168
+ return result;
169
+ void result.catch(() => { });
170
+ throw new Error("Lod: three's compileAsync took no render context as it started (lod mirrors three r186)");
171
+ }
172
+ //# sourceMappingURL=pipelines.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"pipelines.js","sourceRoot":"","sources":["../../../src/levels/compile/pipelines.ts"],"names":[],"mappings":"AAOA,sBAAsB;AACtB,MAAM,CAAC,MAAM,KAAK,GAAG,GAAG,EAAE,CAAC,IAAI,OAAO,CAAO,CAAC,OAAO,EAAE,EAAE,CAAC,qBAAqB,CAAC,GAAG,EAAE,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;AAElG,MAAM,WAAW,GAAG,CAAC,KAAc,EAAsB,EAAE,CACzD,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,IAAI,OAAO,OAAO,CAAC,GAAG,CAAC,KAAK,EAAE,cAAc,CAAC,KAAK,UAAU,CAAC;AAE1G;;;;;;GAMG;AACH,MAAM,UAAU,cAAc,CAAC,QAAkB;IAC/C,MAAM,SAAS,GAAY,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,YAAY,CAAC,CAAC;IAC/D,IAAI,CAAC,WAAW,CAAC,SAAS,CAAC;QAAE,MAAM,IAAI,KAAK,CAAC,oEAAoE,CAAC,CAAC;IACnH,MAAM,GAAG,GAAG,SAAS,CAAC,YAAY,CAAC;IACnC,MAAM,OAAO,GAAG,IAAI,OAAO,EAAyB,CAAC;IACrD,SAAS,CAAC,YAAY,GAAG,CAAC,MAAM,EAAE,QAAQ,EAAE,EAAE;QAC5C,MAAM,MAAM,GAAG,QAAQ,EAAE,MAAM,IAAI,CAAC,CAAC;QACrC,MAAM,QAAQ,GAAG,GAAG,CAAC,IAAI,CAAC,SAAS,EAAE,MAAM,EAAE,QAAQ,CAAC,CAAC;QACvD,IAAI,CAAC,QAAQ;YAAE,OAAO,QAAQ,CAAC;QAC/B,IAAI,OAAO,QAAQ,KAAK,QAAQ,IAAI,QAAQ,KAAK,IAAI;YAAE,MAAM,IAAI,KAAK,CAAC,wCAAwC,CAAC,CAAC;QACjH,IAAI,KAAK,GAAG,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;QAClC,IAAI,CAAC,KAAK,EAAE,CAAC;YACX,KAAK,GAAG,aAAa,CAAC,QAAQ,EAAE,QAAQ,EAAE,QAAQ,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC;YAClE,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,KAAK,CAAC,CAAC;YAC7B,MAAM,KAAK,GAAG,GAAG,EAAE,CAAC,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;YAC7C,KAAK,KAAK,CAAC,IAAI,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC;QAChC,CAAC;QACD,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QACrB,OAAO,QAAQ,CAAC;IAClB,CAAC,CAAC;AACJ,CAAC;AAED;;;GAGG;AACH,KAAK,UAAU,aAAa,CAAC,QAAkB,EAAE,QAAgB,EAAE,OAAoC;IACrG,MAAM,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;IAC3B,MAAM,GAAG,GAAY,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC;IAC1D,IAAI,OAAO,GAAG,KAAK,UAAU;QAAE,MAAM,IAAI,KAAK,CAAC,6CAA6C,CAAC,CAAC;IAC9F,SAAS,CAAC;QACR,MAAM,IAAI,GAAY,OAAO,CAAC,KAAK,CAAC,GAAG,EAAE,QAAQ,CAAC,OAAO,EAAE,CAAC,QAAQ,CAAC,CAAC,CAAC;QACvE,IAAI,OAAO,IAAI,KAAK,QAAQ,IAAI,IAAI,KAAK,IAAI;YAAE,MAAM,IAAI,KAAK,CAAC,kDAAkD,CAAC,CAAC;QACnH,IAAI,OAAO,CAAC,GAAG,CAAC,IAAI,EAAE,OAAO,CAAC,KAAK,IAAI;YAAE,MAAM,IAAI,KAAK,CAAC,yCAAyC,CAAC,CAAC;QACpG,IAAI,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,eAAe,CAAC,KAAK,IAAI;YAAE,MAAM,IAAI,KAAK,CAAC,oDAAoD,CAAC,CAAC;QAC3H,IAAI,OAAO,CAAC,GAAG,CAAC,IAAI,EAAE,UAAU,CAAC;YAAE,OAAO;QAC1C,MAAM,KAAK,EAAE,CAAC;IAChB,CAAC;AACH,CAAC;AAQD;;;;GAIG;AACH,MAAM,UAAU,GAAG,CAAC,WAAW,EAAE,WAAW,EAAE,cAAc,EAAE,MAAM,EAAE,iBAAiB,EAAE,mBAAmB,EAAE,kBAAkB,CAAC,CAAC;AAClI,+FAA+F;AAC/F,MAAM,KAAK,GAAG,CAAC,UAAU,EAAE,iBAAiB,EAAE,mBAAmB,EAAE,kBAAkB,CAAC,CAAC;AAEvF;;;;;GAKG;AACH,SAAS,gBAAgB,CAAC,QAAkB;IAC1C,MAAM,IAAI,GAAG,QAAQ,CAAC,KAAK,EAAE,CAAC;IAC9B,sHAAsH;IACtH,gHAAgH;IAChH,KAAK,MAAM,GAAG,IAAI,CAAC,GAAG,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,EAAE,GAAG,KAAK,CAAC;QACpD,IAAI,CAAC,GAAG,CAAC,UAAU,CAAC,GAAG,CAAC,IAAI,CAAC,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,GAAG,CAAC;YAAE,OAAO,CAAC,GAAG,CAAC,IAAI,EAAE,GAAG,EAAE,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,GAAG,CAAC,IAAI,IAAI,CAAC,CAAC;IACpH,KAAK,MAAM,GAAG,IAAI,UAAU,EAAE,CAAC;QAC7B,IAAI,KAAK,GAAY,OAAO,CAAC,GAAG,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC;QAC5C,IAAI,KAAK,GAAG,KAAK,CAAC;QAClB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,EAAE;YAC/B,GAAG,EAAE,GAAG,EAAE,CAAC,KAAK;YAChB,GAAG,EAAE,CAAC,IAAa,EAAE,EAAE;gBACrB,IAAI,KAAK;oBAAE,OAAO;gBAClB,KAAK,GAAG,IAAI,CAAC;gBACb,KAAK,GAAG,IAAI,CAAC;YACf,CAAC;SACF,CAAC,CAAC;IACL,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,QAAkB,EAAE,IAAU,EAAE,EAAE,OAAO,EAAE,gBAAgB,EAAiB;IACtG,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,GAAG,OAAO,CAAC;IAClC,MAAM,MAAM,GAAG,QAAQ,CAAC,eAAe,EAAE,CAAC;IAC1C,MAAM,GAAG,GAAG,QAAQ,CAAC,MAAM,EAAE,CAAC;IAC9B,MAAM,QAAQ,GAAG,QAAQ,CAAC,iBAAiB,EAAE,CAAC;IAC9C,MAAM,QAAQ,GAAG,QAAQ,CAAC,oBAAoB,EAAE,CAAC;IACjD,MAAM,MAAM,GAAG,IAAI,CAAC,aAAa,CAAC;IAClC,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC;IAC7B,MAAM,QAAQ,GAAG,IAAI,CAAC,QAAQ,CAAC;IAC/B,MAAM,UAAU,GAAG,KAAK,CAAC,UAAU,CAAC;IACpC,MAAM,cAAc,GAAG,KAAK,CAAC,cAAc,CAAC;IAC5C,MAAM,QAAQ,GAAG,KAAK,CAAC,gBAAgB,CAAC;IACxC,IAAI,CAAC;QACH,QAAQ,CAAC,eAAe,CAAC,OAAO,CAAC,MAAM,EAAE,OAAO,CAAC,QAAQ,EAAE,OAAO,CAAC,QAAQ,CAAC,CAAC;QAC7E,QAAQ,CAAC,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;QAC7B,KAAK,CAAC,gBAAgB,GAAG,gBAAgB,IAAI,gBAAgB,CAAC,gBAAgB,CAAC,CAAC;QAChF,4EAA4E;QAC5E,IAAI,CAAC,aAAa,GAAG,KAAK,CAAC;QAC3B,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC;QACpB,IAAI,CAAC,QAAQ,GAAG,EAAE,CAAC;QACnB,0GAA0G;QAC1G,KAAK,CAAC,UAAU,GAAG,IAAI,CAAC;QACxB,KAAK,CAAC,cAAc,GAAG,IAAI,CAAC;QAC5B,OAAO,OAAO,CAAC,QAAQ,EAAE,OAAO,CAAC,KAAK,EAAE,GAAG,EAAE,CAAC,QAAQ,CAAC,YAAY,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,CAAC,CAAC,CAAC;IAC5F,CAAC;YAAS,CAAC;QACT,KAAK,CAAC,UAAU,GAAG,UAAU,CAAC;QAC9B,KAAK,CAAC,cAAc,GAAG,cAAc,CAAC;QACtC,KAAK,CAAC,gBAAgB,GAAG,QAAQ,CAAC;QAClC,IAAI,CAAC,QAAQ,GAAG,QAAQ,CAAC;QACzB,IAAI,CAAC,aAAa,GAAG,MAAM,CAAC;QAC5B,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;QACvB,QAAQ,CAAC,eAAe,CAAC,MAAM,EAAE,QAAQ,EAAE,QAAQ,CAAC,CAAC;QACrD,QAAQ,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;IACvB,CAAC;AACH,CAAC;AAOD,MAAM,gBAAgB,GAAG,CAAC,KAAc,EAA2B,EAAE,CACnE,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,IAAI,OAAO,OAAO,CAAC,GAAG,CAAC,KAAK,EAAE,KAAK,CAAC,KAAK,UAAU,CAAC;AAEjG;;;;;;GAMG;AACH,MAAM,UAAU,OAAO,CAAC,QAAkB,EAAE,KAAa,EAAE,OAA4B;IACrF,IAAI,KAAK,KAAK,CAAC;QAAE,OAAO,OAAO,EAAE,CAAC;IAClC,MAAM,QAAQ,GAAY,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,iBAAiB,CAAC,CAAC;IACnE,IAAI,CAAC,gBAAgB,CAAC,QAAQ,CAAC;QAAE,MAAM,IAAI,KAAK,CAAC,gDAAgD,CAAC,CAAC;IACnG,MAAM,GAAG,GAAG,MAAM,CAAC,MAAM,CAAC,QAAQ,EAAE,KAAK,CAAC,CAAC;IAC3C,MAAM,GAAG,GAAG,QAAQ,CAAC,GAAG,CAAC;IACzB,IAAI,KAAK,GAAG,KAAK,CAAC;IAClB,MAAM,OAAO,GAAG,GAAG,EAAE;QACnB,IAAI,GAAG;YAAE,QAAQ,CAAC,GAAG,GAAG,GAAG,CAAC;;YACvB,OAAO,CAAC,cAAc,CAAC,QAAQ,EAAE,KAAK,CAAC,CAAC;IAC/C,CAAC,CAAC;IACF,QAAQ,CAAC,GAAG,GAAG,CAAC,MAAM,EAAE,GAAG,EAAE,EAAE;QAC7B,KAAK,GAAG,IAAI,CAAC;QACb,OAAO,EAAE,CAAC;QACV,OAAO,GAAG,CAAC,IAAI,CAAC,QAAQ,EAAE,MAAM,EAAE,GAAG,EAAE,KAAK,CAAC,CAAC;IAChD,CAAC,CAAC;IACF,IAAI,MAAqB,CAAC;IAC1B,IAAI,CAAC;QACH,MAAM,GAAG,OAAO,EAAE,CAAC;IACrB,CAAC;YAAS,CAAC;QACT,IAAI,CAAC,KAAK;YAAE,OAAO,EAAE,CAAC;IACxB,CAAC;IACD,oHAAoH;IACpH,YAAY;IACZ,IAAI,KAAK,IAAI,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,eAAe,CAAC,KAAK,IAAI;QAAE,OAAO,MAAM,CAAC;IAC5E,KAAK,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,GAAE,CAAC,CAAC,CAAC;IAC5B,MAAM,IAAI,KAAK,CAAC,yFAAyF,CAAC,CAAC;AAC7G,CAAC"}
@@ -0,0 +1,29 @@
1
+ import type { RenderContext } from "./compile/contexts.js";
2
+ import type { CameraRequests } from "./requests.js";
3
+ /**
4
+ * A Lod's background compiles of its loaded levels, per render context: which levels each context's compile has
5
+ * started for, so that each compiles once per context, and the compiles still running.
6
+ */
7
+ export declare class ContextCompiles {
8
+ /** Compile the loaded levels of `bits` for `context`. */
9
+ private readonly run;
10
+ /** Called with what a compile throws. */
11
+ private readonly failed;
12
+ /** Per render context, the bits of the levels whose compile for it has started: a context dropped drops its bits. */
13
+ private readonly claimed;
14
+ /** The compiles running, each with the camera whose context it compiles for. */
15
+ private readonly runs;
16
+ constructor(
17
+ /** Compile the loaded levels of `bits` for `context`. */
18
+ run: (context: RenderContext, bits: number) => Promise<void>,
19
+ /** Called with what a compile throws. */
20
+ failed: (error: unknown) => void);
21
+ /** Mark the levels of `bits` as compiling for `context`, and answer those that were not yet. */
22
+ claim(context: RenderContext, bits: number): number;
23
+ /** Compile the loaded levels of `bits` for `context` in the background, once the render that asked for them has ended. */
24
+ compile(context: RenderContext, bits: number): void;
25
+ /** Whether a compile runs for a camera still rendering the Lod: one for a camera that stopped holds nothing up. */
26
+ running(requests: CameraRequests): boolean;
27
+ /** The compiles running, each settling once its compile has ended. */
28
+ tasks(): Iterable<Promise<void>>;
29
+ }
@@ -0,0 +1,50 @@
1
+ import { nextTask } from "../task.js";
2
+ /**
3
+ * A Lod's background compiles of its loaded levels, per render context: which levels each context's compile has
4
+ * started for, so that each compiles once per context, and the compiles still running.
5
+ */
6
+ export class ContextCompiles {
7
+ run;
8
+ failed;
9
+ /** Per render context, the bits of the levels whose compile for it has started: a context dropped drops its bits. */
10
+ claimed = new WeakMap();
11
+ /** The compiles running, each with the camera whose context it compiles for. */
12
+ runs = new Map();
13
+ constructor(
14
+ /** Compile the loaded levels of `bits` for `context`. */
15
+ run,
16
+ /** Called with what a compile throws. */
17
+ failed) {
18
+ this.run = run;
19
+ this.failed = failed;
20
+ }
21
+ /** Mark the levels of `bits` as compiling for `context`, and answer those that were not yet. */
22
+ claim(context, bits) {
23
+ const claimed = this.claimed.get(context) ?? 0;
24
+ this.claimed.set(context, claimed | bits);
25
+ return bits & ~claimed;
26
+ }
27
+ /** Compile the loaded levels of `bits` for `context` in the background, once the render that asked for them has ended. */
28
+ compile(context, bits) {
29
+ if (bits === 0)
30
+ return;
31
+ // A render runs within one task: the next starts after it has ended.
32
+ const done = nextTask()
33
+ .then(() => this.run(context, bits))
34
+ .catch((error) => this.failed(error))
35
+ .finally(() => this.runs.delete(done));
36
+ this.runs.set(done, context.camera);
37
+ }
38
+ /** Whether a compile runs for a camera still rendering the Lod: one for a camera that stopped holds nothing up. */
39
+ running(requests) {
40
+ for (const camera of this.runs.values())
41
+ if (requests.rendering(camera))
42
+ return true;
43
+ return false;
44
+ }
45
+ /** The compiles running, each settling once its compile has ended. */
46
+ tasks() {
47
+ return this.runs.keys();
48
+ }
49
+ }
50
+ //# sourceMappingURL=compiles.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compiles.js","sourceRoot":"","sources":["../../src/levels/compiles.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAItC;;;GAGG;AACH,MAAM,OAAO,eAAe;IAQP;IAEA;IATnB,qHAAqH;IACpG,OAAO,GAAG,IAAI,OAAO,EAAyB,CAAC;IAChE,gFAAgF;IAC/D,IAAI,GAAG,IAAI,GAAG,EAAyB,CAAC;IAEzD;IACE,yDAAyD;IACxC,GAA4D;IAC7E,yCAAyC;IACxB,MAAgC;QAFhC,QAAG,GAAH,GAAG,CAAyD;QAE5D,WAAM,GAAN,MAAM,CAA0B;IAChD,CAAC;IAEJ,gGAAgG;IAChG,KAAK,CAAC,OAAsB,EAAE,IAAY;QACxC,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;QAC/C,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAAC,CAAC;QAC1C,OAAO,IAAI,GAAG,CAAC,OAAO,CAAC;IACzB,CAAC;IAED,0HAA0H;IAC1H,OAAO,CAAC,OAAsB,EAAE,IAAY;QAC1C,IAAI,IAAI,KAAK,CAAC;YAAE,OAAO;QACvB,qEAAqE;QACrE,MAAM,IAAI,GAAG,QAAQ,EAAE;aACpB,IAAI,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,OAAO,EAAE,IAAI,CAAC,CAAC;aACnC,KAAK,CAAC,CAAC,KAAc,EAAE,EAAE,CAAC,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;aAC7C,OAAO,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC;QACzC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,EAAE,OAAO,CAAC,MAAM,CAAC,CAAC;IACtC,CAAC;IAED,mHAAmH;IACnH,OAAO,CAAC,QAAwB;QAC9B,KAAK,MAAM,MAAM,IAAI,IAAI,CAAC,IAAI,CAAC,MAAM,EAAE;YAAE,IAAI,QAAQ,CAAC,SAAS,CAAC,MAAM,CAAC;gBAAE,OAAO,IAAI,CAAC;QACrF,OAAO,KAAK,CAAC;IACf,CAAC;IAED,sEAAsE;IACtE,KAAK;QACH,OAAO,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC;IAC1B,CAAC;CACF"}
@@ -0,0 +1,102 @@
1
+ import { d } from "typegpu";
2
+ /** Share of each level's range over which its finer neighbour fades out. */
3
+ export declare const FADE = 0.1;
4
+ /**
5
+ * The most levels a Lod has. WGSL has no arrays of a size given at run time, so levelsToDraw reads
6
+ * maxPixels from an array of this size, and the loaded sets are bits of one u32. The GPU side passes the array as two
7
+ * vec4s, `low` and `high` (see `levelsToDrawNode`), which hold eight.
8
+ */
9
+ export declare const MAX_LEVELS = 8;
10
+ /**
11
+ * The largest f32, which stands for any height levelsToDraw reads, as the maxPixels of level 0's Infinity: an f32
12
+ * holds Infinity, but WGSL has no literal for it and assumes finite math, so TypeGPU refuses to pass it.
13
+ */
14
+ export declare const ANY_HEIGHT = 3.4028234663852886e+38;
15
+ /**
16
+ * The levels as levelsToDraw reads them, with the draw's settings: `maxPixels` per level, `empty` the bits of the
17
+ * levels that draw nothing, `coarsest` the coarsest level that draws something (level 0 if none does), `forced` the
18
+ * level every draw shows or -1, and `fades` 1 where levels fade (not in an orthographic camera or with a forced level),
19
+ * else 0.
20
+ */
21
+ export declare const DrawLevels: d.WgslStruct<{
22
+ count: d.I32;
23
+ maxPixels: d.WgslArray<d.F32>;
24
+ empty: d.U32;
25
+ coarsest: d.I32;
26
+ forced: d.I32;
27
+ fades: d.U32;
28
+ }>;
29
+ /** Whether bit `level` of `bits` is set: the levels of a set, such as the loaded ones, are bits of one number. */
30
+ export declare const has: (bits: number, level: number) => boolean;
31
+ /** `levels` as levelsToDraw reads them, on the CPU and in the GPU's uniforms; `forced` a forced level or null. */
32
+ export declare function drawLevels(levels: readonly {
33
+ maxPixels: number;
34
+ }[], empty: number, forced: number | null, fades: boolean): d.Infer<typeof DrawLevels>;
35
+ /**
36
+ * What one object draws: `level` with the signed fade `fade`, and `finer` with `-fade` (see fade.ts), so that each
37
+ * pixel is drawn by exactly one of them; with `fade` 0 only `level` draws. `level` -1 draws nothing.
38
+ */
39
+ export declare const Draw: d.WgslStruct<{
40
+ level: d.I32;
41
+ finer: d.I32;
42
+ fade: d.F32;
43
+ }>;
44
+ /**
45
+ * The level that draws most of an object's pixels in `draw`, or null for none. `level` keeps 1 - fade of them and
46
+ * `finer` fade (see fade.ts), so `finer` once fade is above one half; at one half exactly, `level`.
47
+ */
48
+ export declare function drawnLevel({ level, finer, fade }: d.Infer<typeof Draw>): number | null;
49
+ /** The level a `height` px tall object is drawn at: the last one whose maxPixels it fits; level 0 fits any height. */
50
+ export declare const levelForHeight: import("typegpu").TgpuFn<(height: d.F32, levels: d.WgslStruct<{
51
+ count: d.I32;
52
+ maxPixels: d.WgslArray<d.F32>;
53
+ empty: d.U32;
54
+ coarsest: d.I32;
55
+ forced: d.I32;
56
+ fades: d.U32;
57
+ }>) => d.I32>;
58
+ /** `level` once loaded, else the nearest loaded coarser level that draws something, else -1: never a finer one. */
59
+ export declare const loadedOrCoarser: import("typegpu").TgpuFn<(level: d.I32, levels: d.WgslStruct<{
60
+ count: d.I32;
61
+ maxPixels: d.WgslArray<d.F32>;
62
+ empty: d.U32;
63
+ coarsest: d.I32;
64
+ forced: d.I32;
65
+ fades: d.U32;
66
+ }>, loaded: d.U32) => d.I32>;
67
+ /**
68
+ * What an object `height` px tall draws: its level by height (or `levels.forced`), and inside the top FADE of that
69
+ * level's range its finer neighbour too, each as `loaded` has them (see `loadedOrCoarser`). Nothing draws until the
70
+ * coarsest level that draws something has loaded.
71
+ *
72
+ * While a level arrives, `progress` runs from 0 to 1 over the arrival (1 when none is under way) from what the levels
73
+ * of `before` drew to what those of `loaded` draw, with two draws only: the old height fade collapses onto one level,
74
+ * that level hands its pixels to the new one, and the new height fade opens. What arrives where nothing drew draws at
75
+ * once.
76
+ */
77
+ export declare const levelsToDraw: import("typegpu").TgpuFn<(height: d.F32, levels: d.WgslStruct<{
78
+ count: d.I32;
79
+ maxPixels: d.WgslArray<d.F32>;
80
+ empty: d.U32;
81
+ coarsest: d.I32;
82
+ forced: d.I32;
83
+ fades: d.U32;
84
+ }>, loaded: d.U32, before: d.U32, progress: d.F32) => d.WgslStruct<{
85
+ level: d.I32;
86
+ finer: d.I32;
87
+ fade: d.F32;
88
+ }>>;
89
+ /** drawnOf on the GPU, from its inputs as TSL nodes. */
90
+ export declare const levelsToDrawNode: (inputs: {
91
+ height: import("three/webgpu").Node<"float">;
92
+ count: import("three/webgpu").Node<"int">;
93
+ low: import("three/webgpu").Node<"vec4">;
94
+ high: import("three/webgpu").Node<"vec4">;
95
+ empty: import("three/webgpu").Node<"uint">;
96
+ coarsest: import("three/webgpu").Node<"int">;
97
+ forced: import("three/webgpu").Node<"int">;
98
+ fades: import("three/webgpu").Node<"uint">;
99
+ loaded: import("three/webgpu").Node<"uint">;
100
+ before: import("three/webgpu").Node<"uint">;
101
+ progress: import("three/webgpu").Node<"float">;
102
+ }) => import("three/webgpu").Node<"vec3">;