@drawcall/lod 0.0.0-stage → 0.1.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 (175) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +83 -2
  3. package/dist/baked/codec.d.ts +10 -0
  4. package/dist/baked/codec.js +291 -0
  5. package/dist/baked/codec.js.map +1 -0
  6. package/dist/baked/index.d.ts +51 -0
  7. package/dist/baked/index.js +183 -0
  8. package/dist/baked/index.js.map +1 -0
  9. package/dist/baked/interior/faces.d.ts +26 -0
  10. package/dist/baked/interior/faces.js +105 -0
  11. package/dist/baked/interior/faces.js.map +1 -0
  12. package/dist/baked/interior/material.d.ts +31 -0
  13. package/dist/baked/interior/material.js +157 -0
  14. package/dist/baked/interior/material.js.map +1 -0
  15. package/dist/baked/interior/rooms.d.ts +22 -0
  16. package/dist/baked/interior/rooms.js +78 -0
  17. package/dist/baked/interior/rooms.js.map +1 -0
  18. package/dist/baked/low.d.ts +20 -0
  19. package/dist/baked/low.js +75 -0
  20. package/dist/baked/low.js.map +1 -0
  21. package/dist/baked/raster.d.ts +20 -0
  22. package/dist/baked/raster.js +71 -0
  23. package/dist/baked/raster.js.map +1 -0
  24. package/dist/baked/transfer.d.ts +36 -0
  25. package/dist/baked/transfer.js +243 -0
  26. package/dist/baked/transfer.js.map +1 -0
  27. package/dist/baked/unwrap.d.ts +9 -0
  28. package/dist/baked/unwrap.js +167 -0
  29. package/dist/baked/unwrap.js.map +1 -0
  30. package/dist/baked/xatlas.d.ts +2 -0
  31. package/dist/baked/xatlas.js +31 -0
  32. package/dist/baked/xatlas.js.map +1 -0
  33. package/dist/bounds.d.ts +33 -0
  34. package/dist/bounds.js +127 -0
  35. package/dist/bounds.js.map +1 -0
  36. package/dist/dispose.d.ts +5 -0
  37. package/dist/dispose.js +28 -0
  38. package/dist/dispose.js.map +1 -0
  39. package/dist/fade.d.ts +44 -0
  40. package/dist/fade.js +78 -0
  41. package/dist/fade.js.map +1 -0
  42. package/dist/impostor/bake/atlas.d.ts +51 -0
  43. package/dist/impostor/bake/atlas.js +190 -0
  44. package/dist/impostor/bake/atlas.js.map +1 -0
  45. package/dist/impostor/bake/index.d.ts +50 -0
  46. package/dist/impostor/bake/index.js +221 -0
  47. package/dist/impostor/bake/index.js.map +1 -0
  48. package/dist/impostor/bake/materials.d.ts +29 -0
  49. package/dist/impostor/bake/materials.js +156 -0
  50. package/dist/impostor/bake/materials.js.map +1 -0
  51. package/dist/impostor/bake/source.d.ts +3 -0
  52. package/dist/impostor/bake/source.js +23 -0
  53. package/dist/impostor/bake/source.js.map +1 -0
  54. package/dist/impostor/cache.d.ts +15 -0
  55. package/dist/impostor/cache.js +44 -0
  56. package/dist/impostor/cache.js.map +1 -0
  57. package/dist/impostor/codec.d.ts +14 -0
  58. package/dist/impostor/codec.js +137 -0
  59. package/dist/impostor/codec.js.map +1 -0
  60. package/dist/impostor/impostor.d.ts +67 -0
  61. package/dist/impostor/impostor.js +79 -0
  62. package/dist/impostor/impostor.js.map +1 -0
  63. package/dist/impostor/mesh/card.d.ts +38 -0
  64. package/dist/impostor/mesh/card.js +79 -0
  65. package/dist/impostor/mesh/card.js.map +1 -0
  66. package/dist/impostor/mesh/index.d.ts +66 -0
  67. package/dist/impostor/mesh/index.js +174 -0
  68. package/dist/impostor/mesh/index.js.map +1 -0
  69. package/dist/impostor/mesh/material.d.ts +63 -0
  70. package/dist/impostor/mesh/material.js +199 -0
  71. package/dist/impostor/mesh/material.js.map +1 -0
  72. package/dist/impostor/mesh/surface.d.ts +63 -0
  73. package/dist/impostor/mesh/surface.js +162 -0
  74. package/dist/impostor/mesh/surface.js.map +1 -0
  75. package/dist/impostor/mesh/textures.d.ts +4 -0
  76. package/dist/impostor/mesh/textures.js +37 -0
  77. package/dist/impostor/mesh/textures.js.map +1 -0
  78. package/dist/impostor/octahedral.d.ts +29 -0
  79. package/dist/impostor/octahedral.js +83 -0
  80. package/dist/impostor/octahedral.js.map +1 -0
  81. package/dist/index.d.ts +15 -0
  82. package/dist/index.js +16 -0
  83. package/dist/index.js.map +1 -0
  84. package/dist/instanced/args.d.ts +20 -0
  85. package/dist/instanced/args.js +77 -0
  86. package/dist/instanced/args.js.map +1 -0
  87. package/dist/instanced/bounds.d.ts +50 -0
  88. package/dist/instanced/bounds.js +271 -0
  89. package/dist/instanced/bounds.js.map +1 -0
  90. package/dist/instanced/dirty.d.ts +12 -0
  91. package/dist/instanced/dirty.js +61 -0
  92. package/dist/instanced/dirty.js.map +1 -0
  93. package/dist/instanced/index.d.ts +116 -0
  94. package/dist/instanced/index.js +573 -0
  95. package/dist/instanced/index.js.map +1 -0
  96. package/dist/instanced/meshes.d.ts +14 -0
  97. package/dist/instanced/meshes.js +54 -0
  98. package/dist/instanced/meshes.js.map +1 -0
  99. package/dist/instanced/select.d.ts +84 -0
  100. package/dist/instanced/select.js +264 -0
  101. package/dist/instanced/select.js.map +1 -0
  102. package/dist/lazy.d.ts +64 -0
  103. package/dist/lazy.js +187 -0
  104. package/dist/lazy.js.map +1 -0
  105. package/dist/levels.d.ts +72 -0
  106. package/dist/levels.js +146 -0
  107. package/dist/levels.js.map +1 -0
  108. package/dist/loader/cache.d.ts +15 -0
  109. package/dist/loader/cache.js +37 -0
  110. package/dist/loader/cache.js.map +1 -0
  111. package/dist/loader/dispose.d.ts +3 -0
  112. package/dist/loader/dispose.js +25 -0
  113. package/dist/loader/dispose.js.map +1 -0
  114. package/dist/loader.d.ts +99 -0
  115. package/dist/loader.js +234 -0
  116. package/dist/loader.js.map +1 -0
  117. package/dist/lod.d.ts +78 -0
  118. package/dist/lod.js +211 -0
  119. package/dist/lod.js.map +1 -0
  120. package/dist/material.d.ts +12 -0
  121. package/dist/material.js +52 -0
  122. package/dist/material.js.map +1 -0
  123. package/dist/pause.d.ts +6 -0
  124. package/dist/pause.js +20 -0
  125. package/dist/pause.js.map +1 -0
  126. package/dist/renderer.d.ts +21 -0
  127. package/dist/renderer.js +83 -0
  128. package/dist/renderer.js.map +1 -0
  129. package/dist/simplify.d.ts +24 -0
  130. package/dist/simplify.js +148 -0
  131. package/dist/simplify.js.map +1 -0
  132. package/dist/source/error.d.ts +14 -0
  133. package/dist/source/error.js +94 -0
  134. package/dist/source/error.js.map +1 -0
  135. package/dist/source/frame.d.ts +11 -0
  136. package/dist/source/frame.js +25 -0
  137. package/dist/source/frame.js.map +1 -0
  138. package/dist/source/shading.d.ts +96 -0
  139. package/dist/source/shading.js +224 -0
  140. package/dist/source/shading.js.map +1 -0
  141. package/dist/source/source.d.ts +23 -0
  142. package/dist/source/source.js +50 -0
  143. package/dist/source/source.js.map +1 -0
  144. package/dist/source/surface.d.ts +31 -0
  145. package/dist/source/surface.js +110 -0
  146. package/dist/source/surface.js.map +1 -0
  147. package/dist/source/texels.d.ts +45 -0
  148. package/dist/source/texels.js +191 -0
  149. package/dist/source/texels.js.map +1 -0
  150. package/dist/source/trace.d.ts +42 -0
  151. package/dist/source/trace.js +153 -0
  152. package/dist/source/trace.js.map +1 -0
  153. package/dist/three.d.ts +55 -0
  154. package/dist/three.js +103 -0
  155. package/dist/three.js.map +1 -0
  156. package/dist/tsl.d.ts +45 -0
  157. package/dist/tsl.js +99 -0
  158. package/dist/tsl.js.map +1 -0
  159. package/dist/view.d.ts +30 -0
  160. package/dist/view.js +75 -0
  161. package/dist/view.js.map +1 -0
  162. package/dist/wind/bounds.d.ts +3 -0
  163. package/dist/wind/bounds.js +47 -0
  164. package/dist/wind/bounds.js.map +1 -0
  165. package/dist/wind/hooks.d.ts +5 -0
  166. package/dist/wind/hooks.js +3 -0
  167. package/dist/wind/hooks.js.map +1 -0
  168. package/dist/wind/index.d.ts +57 -0
  169. package/dist/wind/index.js +196 -0
  170. package/dist/wind/index.js.map +1 -0
  171. package/dist/wind/sway.d.ts +29 -0
  172. package/dist/wind/sway.js +71 -0
  173. package/dist/wind/sway.js.map +1 -0
  174. package/package.json +69 -3
  175. package/skills/lod/SKILL.md +137 -0
@@ -0,0 +1,271 @@
1
+ import { Box3, Matrix4, Sphere, Vector3 } from "three/webgpu";
2
+ import { FADE } from "../levels.js";
3
+ import { Dirty } from "./dirty.js";
4
+ // Cover float32 matrix products, distances and threshold arithmetic. Near a switch,
5
+ // uncertain blocks keep both levels and cannot reuse a previous GPU selection.
6
+ const ROUND = 1e-5;
7
+ const matrix = new Matrix4();
8
+ const point = new Vector3();
9
+ const extent = new Vector3();
10
+ /** Cached spatial blocks: instance edits refit leaves; moving views visit only blocks. */
11
+ export class Bounds {
12
+ matrices;
13
+ spheres;
14
+ source;
15
+ sphere;
16
+ geometry;
17
+ block;
18
+ leaves;
19
+ tree;
20
+ dirty;
21
+ radii;
22
+ errors;
23
+ unsafe;
24
+ levelBoxes = [];
25
+ token = {};
26
+ changed = false;
27
+ complete = true;
28
+ low = 0;
29
+ high = 0;
30
+ padding = 0;
31
+ constructor(matrices, spheres, source, sphere, draws,
32
+ /** Radius enclosing every placed level about source.center. */
33
+ geometry = source) {
34
+ this.matrices = matrices;
35
+ this.spheres = spheres;
36
+ this.source = source;
37
+ this.sphere = sphere;
38
+ this.geometry = geometry;
39
+ const count = matrices.length / 16;
40
+ // Fine leaves avoid many empty draws in small, multipart crowds. Large crowds
41
+ // retain bounded block traversal rather than inspecting every instance per view.
42
+ this.block = count <= 4096 && draws >= 8 ? 1 : 64;
43
+ this.leaves = 2 ** Math.ceil(Math.log2(Math.max(1, Math.ceil(count / this.block))));
44
+ this.tree = Array.from({ length: this.leaves * 2 }, () => ({
45
+ geometry: new Box3(),
46
+ centers: new Box3(),
47
+ sphere: new Sphere(),
48
+ smallest: Infinity,
49
+ largest: 0,
50
+ reach: 0,
51
+ solid: -1,
52
+ unsafe: false,
53
+ }));
54
+ this.dirty = new Dirty(Math.ceil(count / this.block));
55
+ this.radii = new Float64Array(count);
56
+ this.errors = new Float64Array(count);
57
+ this.unsafe = new Uint8Array(count);
58
+ }
59
+ /** Measure changed matrices, retaining the GPU's max-axis radius for LOD selection. */
60
+ measure(start, end) {
61
+ const { center, radius } = this.source;
62
+ for (let i = start; i < end; i++) {
63
+ matrix.fromArray(this.matrices, i * 16);
64
+ point
65
+ .copy(center)
66
+ .applyMatrix4(matrix)
67
+ .toArray(this.spheres, i * 4);
68
+ const axis = matrix.getMaxScaleOnAxis();
69
+ this.spheres[i * 4 + 3] = radius * axis;
70
+ this.radii[i] = this.geometry.radius * stretch(matrix);
71
+ const e = matrix.elements;
72
+ // Absolute terms also cover cancellation in the shader's transformed center.
73
+ const terms = Math.max(Math.abs(e[0] * center.x) + Math.abs(e[4] * center.y) + Math.abs(e[8] * center.z) + Math.abs(e[12]), Math.abs(e[1] * center.x) + Math.abs(e[5] * center.y) + Math.abs(e[9] * center.z) + Math.abs(e[13]), Math.abs(e[2] * center.x) + Math.abs(e[6] * center.y) + Math.abs(e[10] * center.z) + Math.abs(e[14]), radius, this.geometry.radius);
74
+ this.errors[i] = ROUND * Math.sqrt(3) * terms;
75
+ // WGSL length squares its inputs. Guard the intermediates, not only the final
76
+ // screen height: infinity / infinity would select level zero, not the CPU tier.
77
+ this.unsafe[i] = Number(unsafe(axis) || unsafe(radius) || terms > 1e15 || !Number.isFinite(terms));
78
+ this.dirty.add(Math.floor(i / this.block));
79
+ }
80
+ }
81
+ pad(padding) {
82
+ if (padding === this.padding)
83
+ return;
84
+ this.padding = padding;
85
+ this.dirty.all();
86
+ }
87
+ /** Refit only edited leaves and their ancestors. No instance scan on view changes. */
88
+ refit() {
89
+ if (this.dirty.empty)
90
+ return;
91
+ this.dirty.drain((start, end) => {
92
+ for (let block = start; block < end; block++) {
93
+ this.leaf(at(this.tree, this.leaves + block), block);
94
+ }
95
+ // Join each affected parent once per depth, making a full edit linear in the
96
+ // tree size even when multipart crowds use one leaf per instance.
97
+ let first = Math.floor((this.leaves + start) / 2);
98
+ let last = Math.ceil((this.leaves + end) / 2);
99
+ while (first > 0) {
100
+ for (let index = first; index < last; index++)
101
+ this.join(index);
102
+ first = Math.floor(first / 2);
103
+ last = Math.ceil(last / 2);
104
+ }
105
+ });
106
+ enclosing(at(this.tree, 1).geometry, this.sphere);
107
+ }
108
+ leaf(node, block) {
109
+ node.geometry.makeEmpty();
110
+ node.centers.makeEmpty();
111
+ node.smallest = Infinity;
112
+ node.largest = node.reach = 0;
113
+ node.solid = -1;
114
+ node.unsafe = false;
115
+ const end = Math.min((block + 1) * this.block, this.radii.length);
116
+ for (let i = block * this.block; i < end; i++) {
117
+ const radius = at(this.spheres, i * 4 + 3);
118
+ if (radius === 0 && !at(this.unsafe, i))
119
+ continue;
120
+ node.unsafe ||= Boolean(at(this.unsafe, i));
121
+ const error = at(this.errors, i);
122
+ const reach = at(this.radii, i) * (1 + this.padding) + error;
123
+ point.fromArray(this.spheres, i * 4);
124
+ expand(node.centers, point, error);
125
+ expand(node.geometry, point, reach);
126
+ node.smallest = Math.min(node.smallest, radius);
127
+ node.largest = Math.max(node.largest, radius);
128
+ node.reach = Math.max(node.reach, reach);
129
+ }
130
+ enclosing(node.centers, node.sphere);
131
+ }
132
+ join(index) {
133
+ const node = at(this.tree, index);
134
+ const a = at(this.tree, index * 2);
135
+ const b = at(this.tree, index * 2 + 1);
136
+ node.geometry.copy(a.geometry).union(b.geometry);
137
+ node.centers.copy(a.centers).union(b.centers);
138
+ enclosing(node.centers, node.sphere);
139
+ node.smallest = Math.min(a.smallest, b.smallest);
140
+ node.largest = Math.max(a.largest, b.largest);
141
+ node.reach = Math.max(a.reach, b.reach);
142
+ node.unsafe = a.unsafe || b.unsafe;
143
+ node.solid = -1;
144
+ }
145
+ /** Level bounds plus a token only when every block has an unchanged solid choice. */
146
+ select(levels, view, reaches, measured, root) {
147
+ while (this.levelBoxes.length < levels.length)
148
+ this.levelBoxes.push(new Box3());
149
+ for (const box of this.levelBoxes)
150
+ box.makeEmpty();
151
+ this.complete = measured;
152
+ this.changed = false;
153
+ if (!this.sphere.isEmpty()) {
154
+ if (measured)
155
+ this.visit(1, levels, view);
156
+ else
157
+ for (const box of this.levelBoxes)
158
+ box.copy(at(this.tree, 1).geometry);
159
+ }
160
+ const top = at(this.tree, 1);
161
+ const axis = root.getMaxScaleOnAxis();
162
+ // Three transforms a culling sphere by max-axis scale, which underbounds shear.
163
+ const dilation = axis > 0 ? stretch(root) / axis : 1;
164
+ reaches.forEach((sphere, level) => {
165
+ enclosing(at(this.levelBoxes, level), sphere);
166
+ const next = levels[level + 1];
167
+ if (measured && !top.unsafe && !unsafe(view.scale) && view.eye.length() < 1e15 && !sphere.isEmpty() && !view.ortho && view.forced === null && next) {
168
+ const threshold = next.maxPixels * (view.fades ? 1 - FADE : 1);
169
+ const radius = (2 * top.largest * view.scale * (1 + ROUND * 4)) / threshold + top.reach + view.eye.length() * ROUND;
170
+ if (radius < sphere.radius)
171
+ sphere.set(view.eye, radius);
172
+ }
173
+ if (!sphere.isEmpty())
174
+ sphere.radius *= dilation;
175
+ });
176
+ if (!this.complete)
177
+ return undefined;
178
+ if (this.changed)
179
+ this.token = {};
180
+ return this.token;
181
+ }
182
+ visit(index, levels, view) {
183
+ const node = at(this.tree, index);
184
+ if (node.geometry.isEmpty())
185
+ return;
186
+ this.interval(node, view);
187
+ const low = this.low;
188
+ const high = this.high;
189
+ // Infinity marks an unsafe float32 interval; even legal infinite thresholds
190
+ // cannot exclude the source when the GPU's height may be NaN.
191
+ let finest = view.forced ?? (high === Infinity ? 0 : fitting(levels, high));
192
+ const coarsest = view.forced ?? fitting(levels, low);
193
+ if (view.fades && finest > 0 && high >= at(levels, finest).maxPixels * (1 - FADE) * (1 - ROUND))
194
+ finest--;
195
+ if (finest === coarsest) {
196
+ this.changed ||= node.solid !== finest;
197
+ node.solid = finest;
198
+ at(this.levelBoxes, finest).union(node.geometry);
199
+ return;
200
+ }
201
+ // Descendants may hold a proof from an older split; never reuse that after the
202
+ // whole branch was last selected as one solid level.
203
+ this.changed ||= node.solid !== -1;
204
+ node.solid = -1;
205
+ if (index < this.leaves) {
206
+ this.visit(index * 2, levels, view);
207
+ this.visit(index * 2 + 1, levels, view);
208
+ return;
209
+ }
210
+ this.complete = false;
211
+ for (let level = finest; level <= coarsest; level++)
212
+ at(this.levelBoxes, level).union(node.geometry);
213
+ }
214
+ interval(node, view) {
215
+ const distance = node.sphere.center.distanceTo(view.eye);
216
+ const error = view.eye.length() * ROUND;
217
+ const near = view.ortho ? 1 : Math.max(distance - node.sphere.radius - error, 1e-6);
218
+ const far = view.ortho ? 1 : Math.max(distance + node.sphere.radius + error, 1e-6);
219
+ this.low = ((2 * node.smallest * view.scale) / far) * (1 - ROUND * 4);
220
+ this.high = ((2 * node.largest * view.scale) / near) * (1 + ROUND * 4);
221
+ // Float32 overflow/underflow can invalidate a real-number interval. Keep all
222
+ // levels in these unusual cases instead of making an unsupported proof.
223
+ if (!Number.isFinite(this.high) ||
224
+ this.high > 1e30 ||
225
+ this.low < 1e-30 ||
226
+ node.unsafe ||
227
+ unsafe(view.scale) ||
228
+ distance > 1e15 ||
229
+ view.eye.length() > 1e15) {
230
+ this.low = 0;
231
+ this.high = Infinity;
232
+ }
233
+ }
234
+ }
235
+ /** Upper bound on the largest singular value, exact for orthogonal matrix axes. */
236
+ export function stretch(matrix) {
237
+ const e = matrix.elements;
238
+ const xy = Math.abs(e[0] * e[4] + e[1] * e[5] + e[2] * e[6]);
239
+ const xz = Math.abs(e[0] * e[8] + e[1] * e[9] + e[2] * e[10]);
240
+ const yz = Math.abs(e[4] * e[8] + e[5] * e[9] + e[6] * e[10]);
241
+ return Math.sqrt(Math.max(e[0] ** 2 + e[1] ** 2 + e[2] ** 2 + xy + xz, e[4] ** 2 + e[5] ** 2 + e[6] ** 2 + xy + yz, e[8] ** 2 + e[9] ** 2 + e[10] ** 2 + xz + yz));
242
+ }
243
+ function fitting(levels, height) {
244
+ for (let i = levels.length - 1; i > 0; i--)
245
+ if (height <= at(levels, i).maxPixels)
246
+ return i;
247
+ return 0;
248
+ }
249
+ function expand(box, center, radius) {
250
+ box.expandByPoint(extent.copy(center).addScalar(-radius));
251
+ box.expandByPoint(extent.copy(center).addScalar(radius));
252
+ }
253
+ function at(values, index) {
254
+ const value = values[index];
255
+ if (value === undefined)
256
+ throw new Error(`InstancedLod bounds: index ${index} out of range`);
257
+ return value;
258
+ }
259
+ // These broad limits stay well inside float32's squared-length and product range.
260
+ // Outside them, retain all levels and let the GPU make the original selection.
261
+ function unsafe(value) {
262
+ return !Number.isFinite(value) || Math.abs(value) > 1e15 || (value !== 0 && Math.abs(value) < 1e-15);
263
+ }
264
+ function enclosing(box, sphere) {
265
+ box.getBoundingSphere(sphere);
266
+ if (!Number.isFinite(sphere.radius) || !Number.isFinite(sphere.center.lengthSq())) {
267
+ sphere.center.set(0, 0, 0);
268
+ sphere.radius = Infinity;
269
+ }
270
+ }
271
+ //# sourceMappingURL=bounds.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"bounds.js","sourceRoot":"","sources":["../../src/instanced/bounds.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAC9D,OAAO,EAAE,IAAI,EAAiB,MAAM,cAAc,CAAC;AACnD,OAAO,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAEnC,oFAAoF;AACpF,+EAA+E;AAC/E,MAAM,KAAK,GAAG,IAAI,CAAC;AACnB,MAAM,MAAM,GAAG,IAAI,OAAO,EAAE,CAAC;AAC7B,MAAM,KAAK,GAAG,IAAI,OAAO,EAAE,CAAC;AAC5B,MAAM,MAAM,GAAG,IAAI,OAAO,EAAE,CAAC;AAqB7B,0FAA0F;AAC1F,MAAM,OAAO,MAAM;IAiBE;IACA;IACA;IACR;IAGQ;IAtBF,KAAK,CAAS;IACd,MAAM,CAAS;IACf,IAAI,CAAW;IACf,KAAK,CAAQ;IACb,KAAK,CAAe;IACpB,MAAM,CAAe;IACrB,MAAM,CAAa;IACnB,UAAU,GAAW,EAAE,CAAC;IACjC,KAAK,GAAW,EAAE,CAAC;IACnB,OAAO,GAAG,KAAK,CAAC;IAChB,QAAQ,GAAG,IAAI,CAAC;IAChB,GAAG,GAAG,CAAC,CAAC;IACR,IAAI,GAAG,CAAC,CAAC;IACT,OAAO,GAAG,CAAC,CAAC;IAEpB,YACmB,QAAsB,EACtB,OAAqB,EACrB,MAAc,EACtB,MAAc,EACvB,KAAa;IACb,+DAA+D;IAC9C,WAAwC,MAAM;QAN9C,aAAQ,GAAR,QAAQ,CAAc;QACtB,YAAO,GAAP,OAAO,CAAc;QACrB,WAAM,GAAN,MAAM,CAAQ;QACtB,WAAM,GAAN,MAAM,CAAQ;QAGN,aAAQ,GAAR,QAAQ,CAAsC;QAE/D,MAAM,KAAK,GAAG,QAAQ,CAAC,MAAM,GAAG,EAAE,CAAC;QACnC,8EAA8E;QAC9E,iFAAiF;QACjF,IAAI,CAAC,KAAK,GAAG,KAAK,IAAI,IAAI,IAAI,KAAK,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;QAClD,IAAI,CAAC,MAAM,GAAG,CAAC,IAAI,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,IAAI,CAAC,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC;QACpF,IAAI,CAAC,IAAI,GAAG,KAAK,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,GAAG,CAAC,EAAE,EAAE,GAAG,EAAE,CAAC,CAAC;YACzD,QAAQ,EAAE,IAAI,IAAI,EAAE;YACpB,OAAO,EAAE,IAAI,IAAI,EAAE;YACnB,MAAM,EAAE,IAAI,MAAM,EAAE;YACpB,QAAQ,EAAE,QAAQ;YAClB,OAAO,EAAE,CAAC;YACV,KAAK,EAAE,CAAC;YACR,KAAK,EAAE,CAAC,CAAC;YACT,MAAM,EAAE,KAAK;SACd,CAAC,CAAC,CAAC;QACJ,IAAI,CAAC,KAAK,GAAG,IAAI,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC;QACtD,IAAI,CAAC,KAAK,GAAG,IAAI,YAAY,CAAC,KAAK,CAAC,CAAC;QACrC,IAAI,CAAC,MAAM,GAAG,IAAI,YAAY,CAAC,KAAK,CAAC,CAAC;QACtC,IAAI,CAAC,MAAM,GAAG,IAAI,UAAU,CAAC,KAAK,CAAC,CAAC;IACtC,CAAC;IAED,uFAAuF;IACvF,OAAO,CAAC,KAAa,EAAE,GAAW;QAChC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC,MAAM,CAAC;QACvC,KAAK,IAAI,CAAC,GAAG,KAAK,EAAE,CAAC,GAAG,GAAG,EAAE,CAAC,EAAE,EAAE,CAAC;YACjC,MAAM,CAAC,SAAS,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC,GAAG,EAAE,CAAC,CAAC;YACxC,KAAK;iBACF,IAAI,CAAC,MAAM,CAAC;iBACZ,YAAY,CAAC,MAAM,CAAC;iBACpB,OAAO,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;YAChC,MAAM,IAAI,GAAG,MAAM,CAAC,iBAAiB,EAAE,CAAC;YACxC,IAAI,CAAC,OAAO,CAAC,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC,GAAG,MAAM,GAAG,IAAI,CAAC;YACxC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,QAAQ,CAAC,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;YACvD,MAAM,CAAC,GAAG,MAAM,CAAC,QAAQ,CAAC;YAC1B,6EAA6E;YAC7E,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CACpB,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EACnG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EACnG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EACpG,MAAM,EACN,IAAI,CAAC,QAAQ,CAAC,MAAM,CACrB,CAAC;YACF,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,GAAG,KAAK,GAAG,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,GAAG,KAAK,CAAC;YAC9C,8EAA8E;YAC9E,gFAAgF;YAChF,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,IAAI,MAAM,CAAC,MAAM,CAAC,IAAI,KAAK,GAAG,IAAI,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC;YACnG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC;QAC7C,CAAC;IACH,CAAC;IAED,GAAG,CAAC,OAAe;QACjB,IAAI,OAAO,KAAK,IAAI,CAAC,OAAO;YAAE,OAAO;QACrC,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;QACvB,IAAI,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC;IACnB,CAAC;IAED,sFAAsF;IACtF,KAAK;QACH,IAAI,IAAI,CAAC,KAAK,CAAC,KAAK;YAAE,OAAO;QAC7B,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,KAAK,EAAE,GAAG,EAAE,EAAE;YAC9B,KAAK,IAAI,KAAK,GAAG,KAAK,EAAE,KAAK,GAAG,GAAG,EAAE,KAAK,EAAE,EAAE,CAAC;gBAC7C,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,MAAM,GAAG,KAAK,CAAC,EAAE,KAAK,CAAC,CAAC;YACvD,CAAC;YACD,6EAA6E;YAC7E,kEAAkE;YAClE,IAAI,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,MAAM,GAAG,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC;YAClD,IAAI,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,MAAM,GAAG,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC;YAC9C,OAAO,KAAK,GAAG,CAAC,EAAE,CAAC;gBACjB,KAAK,IAAI,KAAK,GAAG,KAAK,EAAE,KAAK,GAAG,IAAI,EAAE,KAAK,EAAE;oBAAE,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;gBAChE,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;gBAC9B,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,IAAI,GAAG,CAAC,CAAC,CAAC;YAC7B,CAAC;QACH,CAAC,CAAC,CAAC;QACH,SAAS,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,QAAQ,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;IACpD,CAAC;IAEO,IAAI,CAAC,IAAY,EAAE,KAAa;QACtC,IAAI,CAAC,QAAQ,CAAC,SAAS,EAAE,CAAC;QAC1B,IAAI,CAAC,OAAO,CAAC,SAAS,EAAE,CAAC;QACzB,IAAI,CAAC,QAAQ,GAAG,QAAQ,CAAC;QACzB,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC;QAC9B,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;QAChB,IAAI,CAAC,MAAM,GAAG,KAAK,CAAC;QACpB,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC,GAAG,IAAI,CAAC,KAAK,EAAE,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;QAClE,KAAK,IAAI,CAAC,GAAG,KAAK,GAAG,IAAI,CAAC,KAAK,EAAE,CAAC,GAAG,GAAG,EAAE,CAAC,EAAE,EAAE,CAAC;YAC9C,MAAM,MAAM,GAAG,EAAE,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC;YAC3C,IAAI,MAAM,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,MAAM,EAAE,CAAC,CAAC;gBAAE,SAAS;YAClD,IAAI,CAAC,MAAM,KAAK,OAAO,CAAC,EAAE,CAAC,IAAI,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,CAAC;YAC5C,MAAM,KAAK,GAAG,EAAE,CAAC,IAAI,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC;YACjC,MAAM,KAAK,GAAG,EAAE,CAAC,IAAI,CAAC,KAAK,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,KAAK,CAAC;YAC7D,KAAK,CAAC,SAAS,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;YACrC,MAAM,CAAC,IAAI,CAAC,OAAO,EAAE,KAAK,EAAE,KAAK,CAAC,CAAC;YACnC,MAAM,CAAC,IAAI,CAAC,QAAQ,EAAE,KAAK,EAAE,KAAK,CAAC,CAAC;YACpC,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,QAAQ,EAAE,MAAM,CAAC,CAAC;YAChD,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;YAC9C,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC;QAC3C,CAAC;QACD,SAAS,CAAC,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;IACvC,CAAC;IAEO,IAAI,CAAC,KAAa;QACxB,MAAM,IAAI,GAAG,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QAClC,MAAM,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,KAAK,GAAG,CAAC,CAAC,CAAC;QACnC,MAAM,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,KAAK,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC;QACvC,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC;QACjD,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC;QAC9C,SAAS,CAAC,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QACrC,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,QAAQ,EAAE,CAAC,CAAC,QAAQ,CAAC,CAAC;QACjD,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,OAAO,EAAE,CAAC,CAAC,OAAO,CAAC,CAAC;QAC9C,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC;QACxC,IAAI,CAAC,MAAM,GAAG,CAAC,CAAC,MAAM,IAAI,CAAC,CAAC,MAAM,CAAC;QACnC,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,qFAAqF;IACrF,MAAM,CAAC,MAA2B,EAAE,IAAgB,EAAE,OAAiB,EAAE,QAAiB,EAAE,IAAa;QACvG,OAAO,IAAI,CAAC,UAAU,CAAC,MAAM,GAAG,MAAM,CAAC,MAAM;YAAE,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,IAAI,EAAE,CAAC,CAAC;QAChF,KAAK,MAAM,GAAG,IAAI,IAAI,CAAC,UAAU;YAAE,GAAG,CAAC,SAAS,EAAE,CAAC;QACnD,IAAI,CAAC,QAAQ,GAAG,QAAQ,CAAC;QACzB,IAAI,CAAC,OAAO,GAAG,KAAK,CAAC;QACrB,IAAI,CAAC,IAAI,CAAC,MAAM,CAAC,OAAO,EAAE,EAAE,CAAC;YAC3B,IAAI,QAAQ;gBAAE,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,MAAM,EAAE,IAAI,CAAC,CAAC;;gBACrC,KAAK,MAAM,GAAG,IAAI,IAAI,CAAC,UAAU;oBAAE,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC;QAC9E,CAAC;QACD,MAAM,GAAG,GAAG,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC;QAC7B,MAAM,IAAI,GAAG,IAAI,CAAC,iBAAiB,EAAE,CAAC;QACtC,gFAAgF;QAChF,MAAM,QAAQ,GAAG,IAAI,GAAG,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC;QACrD,OAAO,CAAC,OAAO,CAAC,CAAC,MAAM,EAAE,KAAK,EAAE,EAAE;YAChC,SAAS,CAAC,EAAE,CAAC,IAAI,CAAC,UAAU,EAAE,KAAK,CAAC,EAAE,MAAM,CAAC,CAAC;YAC9C,MAAM,IAAI,GAAG,MAAM,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;YAC/B,IAAI,QAAQ,IAAI,CAAC,GAAG,CAAC,MAAM,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,GAAG,IAAI,IAAI,CAAC,MAAM,CAAC,OAAO,EAAE,IAAI,CAAC,IAAI,CAAC,KAAK,IAAI,IAAI,CAAC,MAAM,KAAK,IAAI,IAAI,IAAI,EAAE,CAAC;gBACnJ,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;gBAC/D,MAAM,MAAM,GAAG,CAAC,CAAC,GAAG,GAAG,CAAC,OAAO,GAAG,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,GAAG,KAAK,GAAG,CAAC,CAAC,CAAC,GAAG,SAAS,GAAG,GAAG,CAAC,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,GAAG,KAAK,CAAC;gBACpH,IAAI,MAAM,GAAG,MAAM,CAAC,MAAM;oBAAE,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC,GAAG,EAAE,MAAM,CAAC,CAAC;YAC3D,CAAC;YACD,IAAI,CAAC,MAAM,CAAC,OAAO,EAAE;gBAAE,MAAM,CAAC,MAAM,IAAI,QAAQ,CAAC;QACnD,CAAC,CAAC,CAAC;QACH,IAAI,CAAC,IAAI,CAAC,QAAQ;YAAE,OAAO,SAAS,CAAC;QACrC,IAAI,IAAI,CAAC,OAAO;YAAE,IAAI,CAAC,KAAK,GAAG,EAAE,CAAC;QAClC,OAAO,IAAI,CAAC,KAAK,CAAC;IACpB,CAAC;IAEO,KAAK,CAAC,KAAa,EAAE,MAA2B,EAAE,IAAgB;QACxE,MAAM,IAAI,GAAG,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QAClC,IAAI,IAAI,CAAC,QAAQ,CAAC,OAAO,EAAE;YAAE,OAAO;QACpC,IAAI,CAAC,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;QAC1B,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC;QACrB,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC;QACvB,4EAA4E;QAC5E,8DAA8D;QAC9D,IAAI,MAAM,GAAG,IAAI,CAAC,MAAM,IAAI,CAAC,IAAI,KAAK,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC,CAAC;QAC5E,MAAM,QAAQ,GAAG,IAAI,CAAC,MAAM,IAAI,OAAO,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;QACrD,IAAI,IAAI,CAAC,KAAK,IAAI,MAAM,GAAG,CAAC,IAAI,IAAI,IAAI,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,SAAS,GAAG,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,GAAG,KAAK,CAAC;YAAE,MAAM,EAAE,CAAC;QAC1G,IAAI,MAAM,KAAK,QAAQ,EAAE,CAAC;YACxB,IAAI,CAAC,OAAO,KAAK,IAAI,CAAC,KAAK,KAAK,MAAM,CAAC;YACvC,IAAI,CAAC,KAAK,GAAG,MAAM,CAAC;YACpB,EAAE,CAAC,IAAI,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;YACjD,OAAO;QACT,CAAC;QACD,+EAA+E;QAC/E,qDAAqD;QACrD,IAAI,CAAC,OAAO,KAAK,IAAI,CAAC,KAAK,KAAK,CAAC,CAAC,CAAC;QACnC,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;QAChB,IAAI,KAAK,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC;YACxB,IAAI,CAAC,KAAK,CAAC,KAAK,GAAG,CAAC,EAAE,MAAM,EAAE,IAAI,CAAC,CAAC;YACpC,IAAI,CAAC,KAAK,CAAC,KAAK,GAAG,CAAC,GAAG,CAAC,EAAE,MAAM,EAAE,IAAI,CAAC,CAAC;YACxC,OAAO;QACT,CAAC;QACD,IAAI,CAAC,QAAQ,GAAG,KAAK,CAAC;QACtB,KAAK,IAAI,KAAK,GAAG,MAAM,EAAE,KAAK,IAAI,QAAQ,EAAE,KAAK,EAAE;YAAE,EAAE,CAAC,IAAI,CAAC,UAAU,EAAE,KAAK,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;IACvG,CAAC;IAEO,QAAQ,CAAC,IAAY,EAAE,IAAgB;QAC7C,MAAM,QAAQ,GAAG,IAAI,CAAC,MAAM,CAAC,MAAM,CAAC,UAAU,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;QACzD,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,GAAG,KAAK,CAAC;QACxC,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,QAAQ,GAAG,IAAI,CAAC,MAAM,CAAC,MAAM,GAAG,KAAK,EAAE,IAAI,CAAC,CAAC;QACpF,MAAM,GAAG,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,QAAQ,GAAG,IAAI,CAAC,MAAM,CAAC,MAAM,GAAG,KAAK,EAAE,IAAI,CAAC,CAAC;QACnF,IAAI,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,GAAG,CAAC,GAAG,CAAC,CAAC,GAAG,KAAK,GAAG,CAAC,CAAC,CAAC;QACtE,IAAI,CAAC,IAAI,GAAG,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,GAAG,KAAK,GAAG,CAAC,CAAC,CAAC;QACvE,6EAA6E;QAC7E,wEAAwE;QACxE,IACE,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC;YAC3B,IAAI,CAAC,IAAI,GAAG,IAAI;YAChB,IAAI,CAAC,GAAG,GAAG,KAAK;YAChB,IAAI,CAAC,MAAM;YACX,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC;YAClB,QAAQ,GAAG,IAAI;YACf,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,GAAG,IAAI,EACxB,CAAC;YACD,IAAI,CAAC,GAAG,GAAG,CAAC,CAAC;YACb,IAAI,CAAC,IAAI,GAAG,QAAQ,CAAC;QACvB,CAAC;IACH,CAAC;CACF;AAED,mFAAmF;AACnF,MAAM,UAAU,OAAO,CAAC,MAAe;IACrC,MAAM,CAAC,GAAG,MAAM,CAAC,QAAQ,CAAC;IAC1B,MAAM,EAAE,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC7D,MAAM,EAAE,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;IAC9D,MAAM,EAAE,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;IAC9D,OAAO,IAAI,CAAC,IAAI,CACd,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,CAAC,CACjJ,CAAC;AACJ,CAAC;AAED,SAAS,OAAO,CAAC,MAA2B,EAAE,MAAc;IAC1D,KAAK,IAAI,CAAC,GAAG,MAAM,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC,GAAG,CAAC,EAAE,CAAC,EAAE;QAAE,IAAI,MAAM,IAAI,EAAE,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,SAAS;YAAE,OAAO,CAAC,CAAC;IAC5F,OAAO,CAAC,CAAC;AACX,CAAC;AAED,SAAS,MAAM,CAAC,GAAS,EAAE,MAAe,EAAE,MAAc;IACxD,GAAG,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,SAAS,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC;IAC1D,GAAG,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC;AAC3D,CAAC;AAED,SAAS,EAAE,CAAI,MAAoB,EAAE,KAAa;IAChD,MAAM,KAAK,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC;IAC5B,IAAI,KAAK,KAAK,SAAS;QAAE,MAAM,IAAI,KAAK,CAAC,8BAA8B,KAAK,eAAe,CAAC,CAAC;IAC7F,OAAO,KAAK,CAAC;AACf,CAAC;AAED,kFAAkF;AAClF,+EAA+E;AAC/E,SAAS,MAAM,CAAC,KAAa;IAC3B,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,IAAI,IAAI,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,IAAI,IAAI,CAAC,KAAK,KAAK,CAAC,IAAI,IAAI,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,KAAK,CAAC,CAAC;AACvG,CAAC;AAED,SAAS,SAAS,CAAC,GAAS,EAAE,MAAc;IAC1C,GAAG,CAAC,iBAAiB,CAAC,MAAM,CAAC,CAAC;IAC9B,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,MAAM,CAAC,QAAQ,EAAE,CAAC,EAAE,CAAC;QAClF,MAAM,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC;QAC3B,MAAM,CAAC,MAAM,GAAG,QAAQ,CAAC;IAC3B,CAAC;AACH,CAAC"}
@@ -0,0 +1,12 @@
1
+ /** Changed indices, drained as ordered runs without scanning unchanged instances. */
2
+ export declare class Dirty {
3
+ private readonly count;
4
+ private readonly bits;
5
+ private readonly words;
6
+ constructor(count: number);
7
+ get empty(): boolean;
8
+ add(index: number): void;
9
+ all(): void;
10
+ /** End is exclusive. Edits made by the visitor are not supported. */
11
+ drain(visit: (start: number, end: number) => void): void;
12
+ }
@@ -0,0 +1,61 @@
1
+ /** Changed indices, drained as ordered runs without scanning unchanged instances. */
2
+ export class Dirty {
3
+ count;
4
+ bits;
5
+ words = [];
6
+ constructor(count) {
7
+ this.count = count;
8
+ this.bits = new Uint32Array(Math.ceil(count / 32));
9
+ }
10
+ get empty() {
11
+ return this.words.length === 0;
12
+ }
13
+ add(index) {
14
+ const word = index >>> 5;
15
+ const before = at(this.bits, word);
16
+ this.bits[word] = before | (1 << (index & 31));
17
+ if (before !== 0)
18
+ return;
19
+ this.words.push(word);
20
+ }
21
+ all() {
22
+ this.words.length = 0;
23
+ this.bits.fill(0xffffffff);
24
+ for (let i = 0; i < this.bits.length; i++)
25
+ this.words.push(i);
26
+ if (this.bits.length > 0 && this.count % 32)
27
+ this.bits[this.bits.length - 1] = 0xffffffff >>> (32 - (this.count % 32));
28
+ }
29
+ /** End is exclusive. Edits made by the visitor are not supported. */
30
+ drain(visit) {
31
+ let start = -1;
32
+ let end = -1;
33
+ this.words.sort((a, b) => a - b);
34
+ for (const word of this.words) {
35
+ let bits = at(this.bits, word);
36
+ this.bits[word] = 0;
37
+ while (bits !== 0) {
38
+ const index = word * 32 + 31 - Math.clz32(bits & -bits);
39
+ bits &= bits - 1;
40
+ if (index === end) {
41
+ end++;
42
+ continue;
43
+ }
44
+ if (start >= 0)
45
+ visit(start, end);
46
+ start = index;
47
+ end = index + 1;
48
+ }
49
+ }
50
+ this.words.length = 0;
51
+ if (start >= 0)
52
+ visit(start, end);
53
+ }
54
+ }
55
+ function at(values, index) {
56
+ const value = values[index];
57
+ if (value === undefined)
58
+ throw new Error(`Dirty: index ${index} out of range`);
59
+ return value;
60
+ }
61
+ //# sourceMappingURL=dirty.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dirty.js","sourceRoot":"","sources":["../../src/instanced/dirty.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,116 @@
1
+ import { type Color, Matrix4, Object3D, Sphere, type Camera, type Intersection, type Raycaster } from "three/webgpu";
2
+ import { type LodLevel } from "../levels.js";
3
+ import { type LevelsEventMap } from "../lazy.js";
4
+ import { WIND_BOUNDS } from "../wind/hooks.js";
5
+ /**
6
+ * `count` copies of one object with levels of detail, each switched by its own height on
7
+ * screen: `Lod` for instances. The GPU sorts the instances into levels once per view
8
+ * (see select.ts) and every mesh of a level draws the instances it holds in one indirect
9
+ * draw; an instance near a switch is in both neighbours and they split its pixels with
10
+ * the dither. Thresholds, `forceLevel`, `Lod.quality`, `Lod.debug` and shadows work as
11
+ * for `Lod`; nothing of an instance is drawn into a directional light's shadow map whose
12
+ * texels are wider than it. Each level is culled by the crowd's bounds, tightened for
13
+ * finer levels to the region near the camera where their instances can draw.
14
+ *
15
+ * Instance matrices are model transforms of the object, as for an InstancedMesh; set
16
+ * them with `setMatrixAt`, and instance colours with `setColorAt`. An instance at scale 0
17
+ * draws nothing. Its own transform (and its parents') should scale uniformly; instances
18
+ * may scale any way.
19
+ *
20
+ * Levels are templates, read when it is built: their meshes are drawn instanced, not
21
+ * added to the scene. They cannot contain skinned meshes, InstancedMeshes (other than an
22
+ * ImpostorMesh) or nested Lods. To build a hierarchy on top, leave level 0 empty (see
23
+ * `Lod`) and draw the detail of the instances `levelOf` reports at level 0 yourself.
24
+ */
25
+ export declare class InstancedLod extends Object3D<LevelsEventMap> {
26
+ readonly isLOD = true;
27
+ readonly isInstancedLod = true;
28
+ /** Let the renderer call `update` with its camera every frame. */
29
+ autoUpdate: boolean;
30
+ /** Draw only this level for every instance, without fades. */
31
+ forceLevel: number | null;
32
+ readonly levels: readonly LodLevel[];
33
+ readonly count: number;
34
+ private readonly entries;
35
+ /** Per level, the meshes drawing it. */
36
+ private readonly meshes;
37
+ private readonly probes;
38
+ private selection;
39
+ private fallback;
40
+ private readonly installed;
41
+ private disposed;
42
+ /** Instance matrices, 16 floats each: the selection uploads them from here. */
43
+ private readonly matrices;
44
+ /** Instance colours, 4 floats each, once `setColorAt` was called. */
45
+ private colors;
46
+ /** Each instance's bounding sphere, centre and radius, in the InstancedLod's space. */
47
+ private readonly spheres;
48
+ /** Bounding sphere of the source in an instance's space. */
49
+ private readonly sphere;
50
+ /** Every placed level, kept separate from the source sphere used for LOD selection. */
51
+ private readonly envelope;
52
+ private readonly rest;
53
+ /** Around every instance; each level may use tighter bounds. */
54
+ readonly bounds: Sphere;
55
+ /** Per level, what its meshes are culled by: `bounds`, or less where its instances must be near the camera. */
56
+ private readonly reaches;
57
+ /** Logical demand at the initial default viewport, separate from first-draw visibility. */
58
+ private readonly demand;
59
+ /** Source-radius padding for the shadow caster cutoff; culling pads every level separately. */
60
+ private padding;
61
+ private readonly matrixChanges;
62
+ private readonly colorChanges;
63
+ private blocks;
64
+ private readonly last;
65
+ /** `levels[0]` is the source. Empty only as the target of `copy`. */
66
+ constructor(levels?: Object3D[], count?: number);
67
+ private build;
68
+ /** Install ready atlas templates atomically before selecting this view. */
69
+ private refresh;
70
+ /** Bound what the level meshes draw, including template placement and impostor boxes. */
71
+ private boundLevels;
72
+ /** Material group `group` of `template` drawn for every instance in `level`'s slots, from indirect draw arguments at byte `offset`. */
73
+ private instance;
74
+ private bind;
75
+ setMatrixAt(index: number, matrix: Matrix4): void;
76
+ getMatrixAt(index: number, matrix: Matrix4): Matrix4;
77
+ /** Tint instance `index` by `color`, as InstancedMesh.setColorAt does, in every level. */
78
+ setColorAt(index: number, color: Color): void;
79
+ /** Instance `index`'s colour: white unless set. */
80
+ getColorAt(index: number, color: Color): Color;
81
+ /** Carry `colors` with the instances from now on: every level's meshes draw them. */
82
+ private useColors;
83
+ /**
84
+ * The finest level instance `index` drew in the last update, or null before the first
85
+ * (or at scale 0). Inside a fade the next coarser level draws too.
86
+ */
87
+ levelOf(index: number): number | null;
88
+ private check;
89
+ /** Source radius padded for the level shaders' shadow caster cutoff. */
90
+ private get drawRadius();
91
+ [WIND_BOUNDS](padding: number, slope: number, baseY: number): void;
92
+ /** Measure only changed matrices; matrix and colour uploads have separate ranges. */
93
+ private measure;
94
+ private measureChanges;
95
+ /** Sort the instances into levels for `camera`; three's renderer calls this itself while `autoUpdate`. */
96
+ update(camera: Camera): void;
97
+ /** Only levels whose conservative bounds contain a possible selected instance. */
98
+ private showLevels;
99
+ /**
100
+ * Hits every instance's source level, with `instanceId` set; `object` is this
101
+ * InstancedLod. Meshes of the source on layers the raycaster does not test are skipped.
102
+ */
103
+ raycast(raycaster: Raycaster, intersects: Intersection[]): boolean;
104
+ /**
105
+ * Copies `source`'s levels, instances and settings into this empty InstancedLod of the
106
+ * same count (it throws otherwise); the copy shares geometry and textures with `source`.
107
+ */
108
+ copy(source: InstancedLod): this;
109
+ clone(): this;
110
+ /**
111
+ * Frees every level, the source included, and the instanced meshes. Clones share
112
+ * geometry and textures, so dispose only once no clone draws any more.
113
+ */
114
+ dispose(): void;
115
+ private clearDraws;
116
+ }