@3driseai/3drise-viewer 0.1.26 → 0.1.28

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 (476) hide show
  1. package/dist/animationsV2/ClipPlayer.d.ts +3 -0
  2. package/dist/animationsV2/ClipPlayer.d.ts.map +1 -1
  3. package/dist/animationsV2/ClipPlayer.js +67 -8
  4. package/dist/animationsV2/ClipsRuntime.d.ts +39 -0
  5. package/dist/animationsV2/ClipsRuntime.d.ts.map +1 -1
  6. package/dist/animationsV2/ClipsRuntime.js +245 -14
  7. package/dist/animationsV2/appliers.d.ts +5 -0
  8. package/dist/animationsV2/appliers.d.ts.map +1 -1
  9. package/dist/animationsV2/appliers.js +25 -7
  10. package/dist/animationsV2/index.d.ts +1 -1
  11. package/dist/animationsV2/index.d.ts.map +1 -1
  12. package/dist/animationsV2/normalize.d.ts.map +1 -1
  13. package/dist/animationsV2/normalize.js +18 -7
  14. package/dist/animationsV2/sequenceUtils.d.ts +42 -1
  15. package/dist/animationsV2/sequenceUtils.d.ts.map +1 -1
  16. package/dist/animationsV2/sequenceUtils.js +103 -3
  17. package/dist/animationsV2/types.d.ts +20 -0
  18. package/dist/animationsV2/types.d.ts.map +1 -1
  19. package/dist/components/AdvancedGrid.d.ts +8 -2
  20. package/dist/components/AdvancedGrid.d.ts.map +1 -1
  21. package/dist/components/AdvancedGrid.js +31 -14
  22. package/dist/components/AnimatedObject.d.ts.map +1 -1
  23. package/dist/components/AnimatedObject.js +7 -5
  24. package/dist/components/ApollonianGrid.d.ts +25 -0
  25. package/dist/components/ApollonianGrid.d.ts.map +1 -0
  26. package/dist/components/ApollonianGrid.js +80 -0
  27. package/dist/components/Bubbles.d.ts +7 -1
  28. package/dist/components/Bubbles.d.ts.map +1 -1
  29. package/dist/components/Bubbles.js +42 -22
  30. package/dist/components/ChladniGrid.d.ts +8 -4
  31. package/dist/components/ChladniGrid.d.ts.map +1 -1
  32. package/dist/components/ChladniGrid.js +31 -13
  33. package/dist/components/CircuitGrid.d.ts +8 -11
  34. package/dist/components/CircuitGrid.d.ts.map +1 -1
  35. package/dist/components/CircuitGrid.js +31 -13
  36. package/dist/components/CloudsGenerator.d.ts +1 -1
  37. package/dist/components/CloudsGenerator.js +1 -1
  38. package/dist/components/ConformalGrid.d.ts +25 -0
  39. package/dist/components/ConformalGrid.d.ts.map +1 -0
  40. package/dist/components/ConformalGrid.js +97 -0
  41. package/dist/components/ContourGrid.d.ts +8 -14
  42. package/dist/components/ContourGrid.d.ts.map +1 -1
  43. package/dist/components/ContourGrid.js +31 -13
  44. package/dist/components/EffectsGenerator.d.ts +7 -1
  45. package/dist/components/EffectsGenerator.d.ts.map +1 -1
  46. package/dist/components/EffectsGenerator.js +39 -38
  47. package/dist/components/EnvironmentManager.d.ts +4 -4
  48. package/dist/components/EnvironmentManager.d.ts.map +1 -1
  49. package/dist/components/FlowNetGrid.d.ts +8 -4
  50. package/dist/components/FlowNetGrid.d.ts.map +1 -1
  51. package/dist/components/FlowNetGrid.js +31 -13
  52. package/dist/components/FractalGrid.d.ts +8 -12
  53. package/dist/components/FractalGrid.d.ts.map +1 -1
  54. package/dist/components/FractalGrid.js +31 -13
  55. package/dist/components/GirihGrid.d.ts +8 -1
  56. package/dist/components/GirihGrid.d.ts.map +1 -1
  57. package/dist/components/GirihGrid.js +31 -13
  58. package/dist/components/Glyphs.d.ts +7 -1
  59. package/dist/components/Glyphs.d.ts.map +1 -1
  60. package/dist/components/Glyphs.js +40 -34
  61. package/dist/components/GravWaveGrid.d.ts +8 -1
  62. package/dist/components/GravWaveGrid.d.ts.map +1 -1
  63. package/dist/components/GravWaveGrid.js +31 -13
  64. package/dist/components/GridsGenerator.d.ts +9 -3
  65. package/dist/components/GridsGenerator.d.ts.map +1 -1
  66. package/dist/components/GridsGenerator.js +41 -18
  67. package/dist/components/HexGrid.d.ts +8 -10
  68. package/dist/components/HexGrid.d.ts.map +1 -1
  69. package/dist/components/HexGrid.js +31 -13
  70. package/dist/components/HilbertGrid.d.ts +25 -0
  71. package/dist/components/HilbertGrid.d.ts.map +1 -0
  72. package/dist/components/HilbertGrid.js +93 -0
  73. package/dist/components/HyperbolicGrid.d.ts +8 -4
  74. package/dist/components/HyperbolicGrid.d.ts.map +1 -1
  75. package/dist/components/HyperbolicGrid.js +31 -13
  76. package/dist/components/LandscapeBuilder.d.ts +1 -1
  77. package/dist/components/LandscapeBuilder.d.ts.map +1 -1
  78. package/dist/components/LandscapeBuilder.js +1 -1
  79. package/dist/components/LandscapeObject.d.ts +1 -1
  80. package/dist/components/LandscapeObject.d.ts.map +1 -1
  81. package/dist/components/LandscapeObject.js +1 -1
  82. package/dist/components/LensingGrid.d.ts +25 -0
  83. package/dist/components/LensingGrid.d.ts.map +1 -0
  84. package/dist/components/LensingGrid.js +81 -0
  85. package/dist/components/MoireGrid.d.ts +8 -12
  86. package/dist/components/MoireGrid.d.ts.map +1 -1
  87. package/dist/components/MoireGrid.js +31 -13
  88. package/dist/components/ObjectNode.d.ts.map +1 -1
  89. package/dist/components/ObjectNode.js +2 -2
  90. package/dist/components/ObjectsRenderer.d.ts.map +1 -1
  91. package/dist/components/ObjectsRenderer.js +37 -3
  92. package/dist/components/OceanBuilder.d.ts +1 -1
  93. package/dist/components/OceanBuilder.js +1 -1
  94. package/dist/components/ParastichyGrid.d.ts +25 -0
  95. package/dist/components/ParastichyGrid.d.ts.map +1 -0
  96. package/dist/components/ParastichyGrid.js +82 -0
  97. package/dist/components/ParticlesGenerator.d.ts.map +1 -1
  98. package/dist/components/ParticlesGenerator.js +6 -0
  99. package/dist/components/PhyllotaxisGrid.d.ts +25 -0
  100. package/dist/components/PhyllotaxisGrid.d.ts.map +1 -0
  101. package/dist/components/PhyllotaxisGrid.js +95 -0
  102. package/dist/components/QuasiGrid.d.ts +8 -11
  103. package/dist/components/QuasiGrid.d.ts.map +1 -1
  104. package/dist/components/QuasiGrid.js +31 -13
  105. package/dist/components/RadarGrid.d.ts +8 -13
  106. package/dist/components/RadarGrid.d.ts.map +1 -1
  107. package/dist/components/RadarGrid.js +31 -13
  108. package/dist/components/ReactionDiffusionGrid.d.ts +8 -1
  109. package/dist/components/ReactionDiffusionGrid.d.ts.map +1 -1
  110. package/dist/components/ReactionDiffusionGrid.js +33 -139
  111. package/dist/components/SceneBuilder.js +1 -1
  112. package/dist/components/SkySystem.d.ts +1 -1
  113. package/dist/components/SparklesBurst.d.ts +7 -1
  114. package/dist/components/SparklesBurst.d.ts.map +1 -1
  115. package/dist/components/SparklesBurst.js +31 -28
  116. package/dist/components/TerrainBuilder.d.ts +1 -1
  117. package/dist/components/TerrainBuilder.d.ts.map +1 -1
  118. package/dist/components/TerrainBuilder.js +1 -1
  119. package/dist/components/TruchetGrid.d.ts +25 -0
  120. package/dist/components/TruchetGrid.d.ts.map +1 -0
  121. package/dist/components/TruchetGrid.js +82 -0
  122. package/dist/components/VoronoiGrid.d.ts +8 -10
  123. package/dist/components/VoronoiGrid.d.ts.map +1 -1
  124. package/dist/components/VoronoiGrid.js +31 -13
  125. package/dist/components/WallpaperGrid.d.ts +8 -1
  126. package/dist/components/WallpaperGrid.d.ts.map +1 -1
  127. package/dist/components/WallpaperGrid.js +33 -210
  128. package/dist/components/effects/AuraEffect.d.ts +8 -3
  129. package/dist/components/effects/AuraEffect.d.ts.map +1 -1
  130. package/dist/components/effects/AuraEffect.js +49 -24
  131. package/dist/components/effects/AuroraEffect.d.ts +8 -3
  132. package/dist/components/effects/AuroraEffect.d.ts.map +1 -1
  133. package/dist/components/effects/AuroraEffect.js +45 -25
  134. package/dist/components/effects/BlackHoleEffect.d.ts +8 -3
  135. package/dist/components/effects/BlackHoleEffect.d.ts.map +1 -1
  136. package/dist/components/effects/BlackHoleEffect.js +42 -21
  137. package/dist/components/effects/ConstellationEffect.d.ts +8 -3
  138. package/dist/components/effects/ConstellationEffect.d.ts.map +1 -1
  139. package/dist/components/effects/ConstellationEffect.js +49 -23
  140. package/dist/components/effects/DandelionSeedsEffect.d.ts +7 -2
  141. package/dist/components/effects/DandelionSeedsEffect.d.ts.map +1 -1
  142. package/dist/components/effects/DandelionSeedsEffect.js +19 -9
  143. package/dist/components/effects/DataStreamEffect.d.ts +8 -3
  144. package/dist/components/effects/DataStreamEffect.d.ts.map +1 -1
  145. package/dist/components/effects/DataStreamEffect.js +54 -26
  146. package/dist/components/effects/DnaHelixEffect.d.ts +8 -3
  147. package/dist/components/effects/DnaHelixEffect.d.ts.map +1 -1
  148. package/dist/components/effects/DnaHelixEffect.js +62 -30
  149. package/dist/components/effects/FallingLeavesEffect.d.ts +7 -2
  150. package/dist/components/effects/FallingLeavesEffect.d.ts.map +1 -1
  151. package/dist/components/effects/FallingLeavesEffect.js +19 -9
  152. package/dist/components/effects/FieldLinesEffect.d.ts +8 -3
  153. package/dist/components/effects/FieldLinesEffect.d.ts.map +1 -1
  154. package/dist/components/effects/FieldLinesEffect.js +30 -20
  155. package/dist/components/effects/Fire.d.ts +8 -3
  156. package/dist/components/effects/Fire.d.ts.map +1 -1
  157. package/dist/components/effects/Fire.js +47 -10
  158. package/dist/components/effects/FireflySwarmEffect.d.ts +7 -2
  159. package/dist/components/effects/FireflySwarmEffect.d.ts.map +1 -1
  160. package/dist/components/effects/FireflySwarmEffect.js +19 -9
  161. package/dist/components/effects/Flares.d.ts +10 -3
  162. package/dist/components/effects/Flares.d.ts.map +1 -1
  163. package/dist/components/effects/Flares.js +53 -56
  164. package/dist/components/effects/ForcefieldEffect.d.ts +8 -3
  165. package/dist/components/effects/ForcefieldEffect.d.ts.map +1 -1
  166. package/dist/components/effects/ForcefieldEffect.js +52 -33
  167. package/dist/components/effects/GalaxyEffect.d.ts +7 -2
  168. package/dist/components/effects/GalaxyEffect.d.ts.map +1 -1
  169. package/dist/components/effects/GalaxyEffect.js +19 -9
  170. package/dist/components/effects/HarmonicShellEffect.d.ts +8 -3
  171. package/dist/components/effects/HarmonicShellEffect.d.ts.map +1 -1
  172. package/dist/components/effects/HarmonicShellEffect.js +30 -22
  173. package/dist/components/effects/HologramEffect.d.ts +8 -3
  174. package/dist/components/effects/HologramEffect.d.ts.map +1 -1
  175. package/dist/components/effects/HologramEffect.js +52 -23
  176. package/dist/components/effects/IceCrystalsEffect.d.ts +8 -3
  177. package/dist/components/effects/IceCrystalsEffect.d.ts.map +1 -1
  178. package/dist/components/effects/IceCrystalsEffect.js +36 -21
  179. package/dist/components/effects/IceHaloEffect.d.ts +7 -2
  180. package/dist/components/effects/IceHaloEffect.d.ts.map +1 -1
  181. package/dist/components/effects/IceHaloEffect.js +19 -9
  182. package/dist/components/effects/LichtenbergEffect.d.ts +7 -2
  183. package/dist/components/effects/LichtenbergEffect.d.ts.map +1 -1
  184. package/dist/components/effects/LichtenbergEffect.js +19 -9
  185. package/dist/components/effects/LightningEffect.d.ts +8 -3
  186. package/dist/components/effects/LightningEffect.d.ts.map +1 -1
  187. package/dist/components/effects/LightningEffect.js +54 -32
  188. package/dist/components/effects/MoleculesEffect.d.ts +8 -3
  189. package/dist/components/effects/MoleculesEffect.d.ts.map +1 -1
  190. package/dist/components/effects/MoleculesEffect.js +31 -21
  191. package/dist/components/effects/MurmurationEffect.d.ts +7 -2
  192. package/dist/components/effects/MurmurationEffect.d.ts.map +1 -1
  193. package/dist/components/effects/MurmurationEffect.js +19 -9
  194. package/dist/components/effects/NeuralNetworkEffect.d.ts +8 -3
  195. package/dist/components/effects/NeuralNetworkEffect.d.ts.map +1 -1
  196. package/dist/components/effects/NeuralNetworkEffect.js +66 -33
  197. package/dist/components/effects/OrbEffect.d.ts +8 -3
  198. package/dist/components/effects/OrbEffect.d.ts.map +1 -1
  199. package/dist/components/effects/OrbEffect.js +89 -42
  200. package/dist/components/effects/PlanetaryRingsEffect.d.ts +7 -2
  201. package/dist/components/effects/PlanetaryRingsEffect.d.ts.map +1 -1
  202. package/dist/components/effects/PlanetaryRingsEffect.js +19 -9
  203. package/dist/components/effects/PortalEffect.d.ts +8 -3
  204. package/dist/components/effects/PortalEffect.d.ts.map +1 -1
  205. package/dist/components/effects/PortalEffect.js +41 -25
  206. package/dist/components/effects/ShockwaveEffect.d.ts +7 -2
  207. package/dist/components/effects/ShockwaveEffect.d.ts.map +1 -1
  208. package/dist/components/effects/ShockwaveEffect.js +19 -9
  209. package/dist/components/effects/SmokePlumeEffect.d.ts +8 -3
  210. package/dist/components/effects/SmokePlumeEffect.d.ts.map +1 -1
  211. package/dist/components/effects/SmokePlumeEffect.js +30 -20
  212. package/dist/components/effects/SmokeRibbon.d.ts +8 -2
  213. package/dist/components/effects/SmokeRibbon.d.ts.map +1 -1
  214. package/dist/components/effects/SmokeRibbon.js +34 -24
  215. package/dist/components/effects/SmokeRingEffect.d.ts +8 -3
  216. package/dist/components/effects/SmokeRingEffect.d.ts.map +1 -1
  217. package/dist/components/effects/SmokeRingEffect.js +33 -21
  218. package/dist/components/effects/StrangeAttractorEffect.d.ts +8 -3
  219. package/dist/components/effects/StrangeAttractorEffect.d.ts.map +1 -1
  220. package/dist/components/effects/StrangeAttractorEffect.js +30 -20
  221. package/dist/components/effects/VolumetricFogEffect.d.ts +8 -3
  222. package/dist/components/effects/VolumetricFogEffect.d.ts.map +1 -1
  223. package/dist/components/effects/VolumetricFogEffect.js +38 -20
  224. package/dist/components/effects/WaterCausticsEffect.d.ts +7 -2
  225. package/dist/components/effects/WaterCausticsEffect.d.ts.map +1 -1
  226. package/dist/components/effects/WaterCausticsEffect.js +19 -9
  227. package/dist/components/effects/index.d.ts +0 -1
  228. package/dist/components/effects/index.d.ts.map +1 -1
  229. package/dist/components/effects/index.js +0 -1
  230. package/dist/components/index.d.ts +14 -1
  231. package/dist/components/index.d.ts.map +1 -1
  232. package/dist/components/index.js +7 -1
  233. package/dist/components/landscape/LandscapeMesh.js +1 -1
  234. package/dist/components/landscape/types.d.ts +1 -1
  235. package/dist/components/landscape/types.d.ts.map +1 -1
  236. package/dist/components/particles/MagneticBottleParticles.d.ts +17 -0
  237. package/dist/components/particles/MagneticBottleParticles.d.ts.map +1 -0
  238. package/dist/components/particles/MagneticBottleParticles.js +618 -0
  239. package/dist/components/particles/ShapeBurstParticles.d.ts +17 -0
  240. package/dist/components/particles/ShapeBurstParticles.d.ts.map +1 -0
  241. package/dist/components/particles/ShapeBurstParticles.js +588 -0
  242. package/dist/components/particles/ShapeFlowParticles.d.ts +17 -0
  243. package/dist/components/particles/ShapeFlowParticles.d.ts.map +1 -0
  244. package/dist/components/particles/ShapeFlowParticles.js +755 -0
  245. package/dist/components/particles/index.d.ts +6 -0
  246. package/dist/components/particles/index.d.ts.map +1 -1
  247. package/dist/components/particles/index.js +3 -0
  248. package/dist/components/terrain/types.d.ts +1 -1
  249. package/dist/components/terrain/types.d.ts.map +1 -1
  250. package/dist/components/volumetricClouds/VolumetricCloudsPass.d.ts +1 -1
  251. package/dist/components/volumetricClouds/VolumetricCloudsPass.d.ts.map +1 -1
  252. package/dist/components/volumetricClouds/types.d.ts +1 -1
  253. package/dist/components/volumetricClouds/types.d.ts.map +1 -1
  254. package/dist/components/water/types.d.ts +1 -1
  255. package/dist/components/water/types.d.ts.map +1 -1
  256. package/dist/hooks/index.d.ts +2 -0
  257. package/dist/hooks/index.d.ts.map +1 -1
  258. package/dist/hooks/index.js +1 -0
  259. package/dist/hooks/useConfigDriver.d.ts +22 -0
  260. package/dist/hooks/useConfigDriver.d.ts.map +1 -0
  261. package/dist/hooks/useConfigDriver.js +43 -0
  262. package/dist/hooks/useConfigLive.d.ts +1 -1
  263. package/dist/hooks/useConfigLive.d.ts.map +1 -1
  264. package/dist/hooks/useLandscapeMaps.d.ts +1 -1
  265. package/dist/hooks/useLandscapeMaps.d.ts.map +1 -1
  266. package/dist/hooks/useOceanMaterial.d.ts +1 -1
  267. package/dist/hooks/useThunder.d.ts +1 -1
  268. package/dist/index.d.ts +1 -2
  269. package/dist/index.d.ts.map +1 -1
  270. package/dist/index.js +1 -2
  271. package/dist/interactions/index.d.ts +2 -1
  272. package/dist/interactions/index.d.ts.map +1 -1
  273. package/dist/interactions/index.js +1 -1
  274. package/dist/interactions/runner.d.ts +18 -3
  275. package/dist/interactions/runner.d.ts.map +1 -1
  276. package/dist/interactions/runner.js +25 -2
  277. package/dist/operations/catalogue/curlSmoke.d.ts +3 -0
  278. package/dist/operations/catalogue/curlSmoke.d.ts.map +1 -0
  279. package/dist/operations/catalogue/curlSmoke.js +178 -0
  280. package/dist/operations/catalogue/displayImage.d.ts.map +1 -1
  281. package/dist/operations/catalogue/displayImage.js +1 -0
  282. package/dist/operations/catalogue/dissolve.d.ts +3 -0
  283. package/dist/operations/catalogue/dissolve.d.ts.map +1 -0
  284. package/dist/operations/catalogue/dissolve.js +57 -0
  285. package/dist/operations/catalogue/emberAsh.d.ts +3 -0
  286. package/dist/operations/catalogue/emberAsh.d.ts.map +1 -0
  287. package/dist/operations/catalogue/emberAsh.js +171 -0
  288. package/dist/operations/catalogue/fade.d.ts.map +1 -1
  289. package/dist/operations/catalogue/fade.js +1 -0
  290. package/dist/operations/catalogue/flip.d.ts +3 -0
  291. package/dist/operations/catalogue/flip.d.ts.map +1 -0
  292. package/dist/operations/catalogue/flip.js +69 -0
  293. package/dist/operations/catalogue/flock.d.ts +3 -0
  294. package/dist/operations/catalogue/flock.d.ts.map +1 -0
  295. package/dist/operations/catalogue/flock.js +163 -0
  296. package/dist/operations/catalogue/focus.d.ts.map +1 -1
  297. package/dist/operations/catalogue/focus.js +1 -0
  298. package/dist/operations/catalogue/frame.d.ts +3 -0
  299. package/dist/operations/catalogue/frame.d.ts.map +1 -0
  300. package/dist/operations/catalogue/frame.js +44 -0
  301. package/dist/operations/catalogue/frost.d.ts +3 -0
  302. package/dist/operations/catalogue/frost.d.ts.map +1 -0
  303. package/dist/operations/catalogue/frost.js +111 -0
  304. package/dist/operations/catalogue/fxInstances.d.ts +21 -0
  305. package/dist/operations/catalogue/fxInstances.d.ts.map +1 -0
  306. package/dist/operations/catalogue/fxInstances.js +47 -0
  307. package/dist/operations/catalogue/fxPoints.d.ts +22 -0
  308. package/dist/operations/catalogue/fxPoints.d.ts.map +1 -0
  309. package/dist/operations/catalogue/fxPoints.js +70 -0
  310. package/dist/operations/catalogue/glow.d.ts.map +1 -1
  311. package/dist/operations/catalogue/glow.js +2 -1
  312. package/dist/operations/catalogue/heatCracks.d.ts +3 -0
  313. package/dist/operations/catalogue/heatCracks.d.ts.map +1 -0
  314. package/dist/operations/catalogue/heatCracks.js +134 -0
  315. package/dist/operations/catalogue/hologram.d.ts +3 -0
  316. package/dist/operations/catalogue/hologram.d.ts.map +1 -0
  317. package/dist/operations/catalogue/hologram.js +118 -0
  318. package/dist/operations/catalogue/inkBloom.d.ts +3 -0
  319. package/dist/operations/catalogue/inkBloom.d.ts.map +1 -0
  320. package/dist/operations/catalogue/inkBloom.js +156 -0
  321. package/dist/operations/catalogue/ivy.d.ts +13 -0
  322. package/dist/operations/catalogue/ivy.d.ts.map +1 -0
  323. package/dist/operations/catalogue/ivy.js +469 -0
  324. package/dist/operations/catalogue/jelly.d.ts +3 -0
  325. package/dist/operations/catalogue/jelly.d.ts.map +1 -0
  326. package/dist/operations/catalogue/jelly.js +50 -0
  327. package/dist/operations/catalogue/kintsugi.d.ts +3 -0
  328. package/dist/operations/catalogue/kintsugi.d.ts.map +1 -0
  329. package/dist/operations/catalogue/kintsugi.js +173 -0
  330. package/dist/operations/catalogue/lidarScan.d.ts +3 -0
  331. package/dist/operations/catalogue/lidarScan.d.ts.map +1 -0
  332. package/dist/operations/catalogue/lidarScan.js +240 -0
  333. package/dist/operations/catalogue/liquidMetal.d.ts +3 -0
  334. package/dist/operations/catalogue/liquidMetal.d.ts.map +1 -0
  335. package/dist/operations/catalogue/liquidMetal.js +122 -0
  336. package/dist/operations/catalogue/metalize.d.ts +3 -0
  337. package/dist/operations/catalogue/metalize.d.ts.map +1 -0
  338. package/dist/operations/catalogue/metalize.js +135 -0
  339. package/dist/operations/catalogue/moveToFront.d.ts.map +1 -1
  340. package/dist/operations/catalogue/moveToFront.js +1 -0
  341. package/dist/operations/catalogue/orbit.d.ts +3 -0
  342. package/dist/operations/catalogue/orbit.d.ts.map +1 -0
  343. package/dist/operations/catalogue/orbit.js +29 -0
  344. package/dist/operations/catalogue/particleSwarm.d.ts +3 -0
  345. package/dist/operations/catalogue/particleSwarm.d.ts.map +1 -0
  346. package/dist/operations/catalogue/particleSwarm.js +138 -0
  347. package/dist/operations/catalogue/petalPeel.d.ts +3 -0
  348. package/dist/operations/catalogue/petalPeel.d.ts.map +1 -0
  349. package/dist/operations/catalogue/petalPeel.js +137 -0
  350. package/dist/operations/catalogue/petrify.d.ts +3 -0
  351. package/dist/operations/catalogue/petrify.d.ts.map +1 -0
  352. package/dist/operations/catalogue/petrify.js +94 -0
  353. package/dist/operations/catalogue/portal.d.ts +3 -0
  354. package/dist/operations/catalogue/portal.d.ts.map +1 -0
  355. package/dist/operations/catalogue/portal.js +224 -0
  356. package/dist/operations/catalogue/print3d.d.ts +3 -0
  357. package/dist/operations/catalogue/print3d.d.ts.map +1 -0
  358. package/dist/operations/catalogue/print3d.js +275 -0
  359. package/dist/operations/catalogue/rainBeads.d.ts +3 -0
  360. package/dist/operations/catalogue/rainBeads.d.ts.map +1 -0
  361. package/dist/operations/catalogue/rainBeads.js +223 -0
  362. package/dist/operations/catalogue/restPose.d.ts +21 -0
  363. package/dist/operations/catalogue/restPose.d.ts.map +1 -0
  364. package/dist/operations/catalogue/restPose.js +55 -0
  365. package/dist/operations/catalogue/rimLight.d.ts +3 -0
  366. package/dist/operations/catalogue/rimLight.d.ts.map +1 -0
  367. package/dist/operations/catalogue/rimLight.js +72 -0
  368. package/dist/operations/catalogue/sandErosion.d.ts +3 -0
  369. package/dist/operations/catalogue/sandErosion.d.ts.map +1 -0
  370. package/dist/operations/catalogue/sandErosion.js +167 -0
  371. package/dist/operations/catalogue/shaderLayers.d.ts +74 -0
  372. package/dist/operations/catalogue/shaderLayers.d.ts.map +1 -0
  373. package/dist/operations/catalogue/shaderLayers.js +322 -0
  374. package/dist/operations/catalogue/shatter.d.ts +3 -0
  375. package/dist/operations/catalogue/shatter.d.ts.map +1 -0
  376. package/dist/operations/catalogue/shatter.js +267 -0
  377. package/dist/operations/catalogue/silkDrape.d.ts +3 -0
  378. package/dist/operations/catalogue/silkDrape.d.ts.map +1 -0
  379. package/dist/operations/catalogue/silkDrape.js +340 -0
  380. package/dist/operations/catalogue/spin.d.ts +3 -0
  381. package/dist/operations/catalogue/spin.d.ts.map +1 -0
  382. package/dist/operations/catalogue/spin.js +42 -0
  383. package/dist/operations/catalogue/surfaceSample.d.ts +17 -0
  384. package/dist/operations/catalogue/surfaceSample.d.ts.map +1 -0
  385. package/dist/operations/catalogue/surfaceSample.js +187 -0
  386. package/dist/operations/catalogue/swirl.d.ts +3 -0
  387. package/dist/operations/catalogue/swirl.d.ts.map +1 -0
  388. package/dist/operations/catalogue/swirl.js +69 -0
  389. package/dist/operations/catalogue/teleport.d.ts +3 -0
  390. package/dist/operations/catalogue/teleport.d.ts.map +1 -0
  391. package/dist/operations/catalogue/teleport.js +213 -0
  392. package/dist/operations/catalogue/transitionField.d.ts +124 -0
  393. package/dist/operations/catalogue/transitionField.d.ts.map +1 -0
  394. package/dist/operations/catalogue/transitionField.js +278 -0
  395. package/dist/operations/catalogue/unweave.d.ts +3 -0
  396. package/dist/operations/catalogue/unweave.d.ts.map +1 -0
  397. package/dist/operations/catalogue/unweave.js +233 -0
  398. package/dist/operations/catalogue/visibility.d.ts.map +1 -1
  399. package/dist/operations/catalogue/visibility.js +1 -0
  400. package/dist/operations/catalogue/voxelize.d.ts +3 -0
  401. package/dist/operations/catalogue/voxelize.d.ts.map +1 -0
  402. package/dist/operations/catalogue/voxelize.js +148 -0
  403. package/dist/operations/catalogue/warmup.d.ts +22 -0
  404. package/dist/operations/catalogue/warmup.d.ts.map +1 -0
  405. package/dist/operations/catalogue/warmup.js +106 -0
  406. package/dist/operations/catalogue/zoom.d.ts.map +1 -1
  407. package/dist/operations/catalogue/zoom.js +1 -0
  408. package/dist/operations/index.d.ts +4 -2
  409. package/dist/operations/index.d.ts.map +1 -1
  410. package/dist/operations/index.js +4 -2
  411. package/dist/operations/objectEffects.d.ts +46 -0
  412. package/dist/operations/objectEffects.d.ts.map +1 -0
  413. package/dist/operations/objectEffects.js +136 -0
  414. package/dist/operations/registry.d.ts +7 -2
  415. package/dist/operations/registry.d.ts.map +1 -1
  416. package/dist/operations/registry.js +45 -3
  417. package/dist/operations/runtime.d.ts +40 -2
  418. package/dist/operations/runtime.d.ts.map +1 -1
  419. package/dist/operations/runtime.js +164 -8
  420. package/dist/operations/types.d.ts +29 -3
  421. package/dist/operations/types.d.ts.map +1 -1
  422. package/dist/operations/types.js +6 -0
  423. package/dist/operations/useObjectEffectLayers.d.ts +4 -0
  424. package/dist/operations/useObjectEffectLayers.d.ts.map +1 -0
  425. package/dist/operations/useObjectEffectLayers.js +42 -0
  426. package/dist/operations/useOperationsRuntime.d.ts.map +1 -1
  427. package/dist/operations/useOperationsRuntime.js +42 -4
  428. package/dist/presets/landscapePresets.d.ts +1 -1
  429. package/dist/presets/landscapePresets.d.ts.map +1 -1
  430. package/dist/presets/landscapePresets.js +1 -1
  431. package/dist/presets/landscapeTypes.d.ts +1 -1
  432. package/dist/presets/landscapeTypes.d.ts.map +1 -1
  433. package/dist/presets/landscapeTypes.js +1 -1
  434. package/dist/presets/oceanSurfacePresets.d.ts +1 -1
  435. package/dist/presets/terrainPresets.d.ts +1 -1
  436. package/dist/presets/terrainPresets.d.ts.map +1 -1
  437. package/dist/presets/volumetricCloudPresets.d.ts +1 -1
  438. package/dist/types/cloudConfigs.d.ts +2 -309
  439. package/dist/types/cloudConfigs.d.ts.map +1 -1
  440. package/dist/types/cloudConfigs.js +2 -339
  441. package/dist/types/gridConfigs.d.ts +103 -0
  442. package/dist/types/gridConfigs.d.ts.map +1 -1
  443. package/dist/types/index.d.ts +9 -9
  444. package/dist/types/index.d.ts.map +1 -1
  445. package/dist/types/index.js +4 -4
  446. package/dist/types/landscapeConfigs.d.ts +2 -217
  447. package/dist/types/landscapeConfigs.d.ts.map +1 -1
  448. package/dist/types/landscapeConfigs.js +2 -256
  449. package/dist/types/oceanConfigs.d.ts +2 -289
  450. package/dist/types/oceanConfigs.d.ts.map +1 -1
  451. package/dist/types/oceanConfigs.js +2 -380
  452. package/dist/types/terrainConfigs.d.ts +2 -250
  453. package/dist/types/terrainConfigs.d.ts.map +1 -1
  454. package/dist/types/terrainConfigs.js +2 -292
  455. package/dist/utils/cloudUniforms.d.ts +1 -1
  456. package/dist/utils/configAnimations.d.ts +6 -0
  457. package/dist/utils/configAnimations.d.ts.map +1 -1
  458. package/dist/utils/configAnimations.js +14 -0
  459. package/dist/utils/gridConfig.d.ts +19 -0
  460. package/dist/utils/gridConfig.d.ts.map +1 -0
  461. package/dist/utils/gridConfig.js +52 -0
  462. package/dist/utils/handleCloudsAnimations.d.ts +1 -1
  463. package/dist/utils/handleCloudsAnimations.js +1 -1
  464. package/dist/utils/hasHoverAnimation.d.ts.map +1 -1
  465. package/dist/utils/hasHoverAnimation.js +0 -2
  466. package/dist/utils/landscapeUniforms.d.ts +1 -1
  467. package/dist/utils/landscapeUniforms.d.ts.map +1 -1
  468. package/dist/utils/oceanUniforms.d.ts +1 -1
  469. package/dist/utils/particleShape.d.ts +33 -0
  470. package/dist/utils/particleShape.d.ts.map +1 -0
  471. package/dist/utils/particleShape.js +207 -0
  472. package/dist/utils/particleTrails.d.ts.map +1 -1
  473. package/dist/utils/particleTrails.js +29 -14
  474. package/dist/utils/terrainUniforms.d.ts +1 -1
  475. package/dist/utils/terrainUniforms.d.ts.map +1 -1
  476. package/package.json +2 -2
@@ -0,0 +1,755 @@
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ import { useCallback, useEffect, useLayoutEffect, useMemo, useRef } from 'react';
3
+ import * as THREE from 'three';
4
+ import { useFrame } from '@react-three/fiber';
5
+ import { GENERATIVE_PARTICLES_ANIMATABLE } from '@3driseai/3drise-core';
6
+ import { applyConfigKeyframeAnimations, applyConfigMouseMove } from '../../utils/configAnimations.js';
7
+ import { createPointerUniforms, stepPointerField, usePointerField } from '../../utils/pointerField.js';
8
+ import { createTrailUniforms, applyTrailConfig, createCpuTrail } from '../../utils/particleTrails.js';
9
+ import { shapeField } from '../../utils/particleShape.js';
10
+ import { useObjectReady } from '../../hooks/useObjectReady.js';
11
+ import { useConfigLiveHandle } from '../../hooks/useConfigLive.js';
12
+ /**
13
+ * Shape Flow — A wind tunnel of particle streams flowing round an invisible mesh shape: divergence-free flow, wake eddies, streaklines coloured by pressure; the cursor is a second obstacle, a jet or a vortex. Use for tech, aero and product scenes.
14
+ */
15
+ // Shape Flow — a wind tunnel: streams of tracer particles flowing past an invisible mesh shape.
16
+ // Movement: the air is an incompressible flow round the shape. A uniform wind U is written as a
17
+ // vector potential psi = (U x x) / 2 and constrained at the obstacle the Bridson way
18
+ // (curl-noise for procedural fluid flow, 2007): psi' = a(d) psi + (1 - a(d)) n (n . psi), with
19
+ // d the distance to the shape, n its normal and a a smooth ramp over a boundary layer. The
20
+ // velocity u = curl psi' is divergence-free and tangent to the surface, so the streams part
21
+ // at the front, speed round the sides and close behind. Downstream of the shape a wake of
22
+ // ABC (Arnold–Beltrami–Childress) eddies, carried with the wind and faded in behind the body,
23
+ // curls the closing streams. The base flow is precomputed on a grid when the shape changes.
24
+ // Tracers are released on a regular lattice of lanes upstream and advected with RK2, so the
25
+ // picture is a clean set of streaklines.
26
+ // Colour: exact, from Bernoulli: pressure coefficient Cp = 1 - |u|^2 / U^2. High pressure (the
27
+ // stagnation point at the nose, the slow wake) takes `color`; low pressure (fast flow round
28
+ // the shoulders) takes `fastColor`; the fastest flow whitens. Tails fade into trailColor.
29
+ // Mouse (pointerMode, cursor on the camera-facing plane through the object):
30
+ // obstacle — a second, spherical body at the cursor (the potential-flow sphere solution): the
31
+ // streams part round it too.
32
+ // jet — the cursor blows along its own motion: a travelling puff pushes the streams.
33
+ // vortex — a vortex line along the view axis at the cursor: the streams wrap round it.
34
+ // Trails (trailMode): streak = motion blur, comet = streaklines, echo = smoke.
35
+ //
36
+ // Generated from the approved lab module (particle lab, shapes batch). Sim units = object-local / size.
37
+ // config.shape is a mesh-builder geometry config ({ type, ...params }); utils/particleShape builds it with
38
+ // the core mesh builders (createMeshByType) and reads it as a surface.
39
+ // ---------------------------------------------------------------------------------------------
40
+ // Engine features
41
+ // ---------------------------------------------------------------------------------------------
42
+ const QUALITY_SCALE = { low: 0.5, medium: 1, high: 1.6 };
43
+ /** mulberry32 — seeded PRNG, returns a function giving floats in [0,1). */
44
+ function mulberry32(seed) {
45
+ let a = seed >>> 0;
46
+ return function () {
47
+ a = (a + 0x6d2b79f5) >>> 0;
48
+ let t = a;
49
+ t = Math.imul(t ^ (t >>> 15), t | 1);
50
+ t ^= t + Math.imul(t ^ (t >>> 7), t | 61);
51
+ return ((t ^ (t >>> 14)) >>> 0) / 4294967296;
52
+ };
53
+ }
54
+ /** Viewport-height hook so point sizes are pixel-correct at any canvas size. */
55
+ function attachViewH(obj, u) {
56
+ const scratch = new THREE.Vector2();
57
+ obj.onBeforeRender = (renderer) => {
58
+ renderer.getDrawingBufferSize(scratch);
59
+ u.uViewH.value = scratch.y;
60
+ };
61
+ }
62
+ function colorUniform(hex) {
63
+ return { value: new THREE.Color(hex) };
64
+ }
65
+ function qualityScale(q) { return QUALITY_SCALE[q] || 1; }
66
+ function seedMix(base, seed) {
67
+ let h = (base ^ Math.imul((Math.round(seed) | 0) + 0x9e37, 0x85ebca6b)) >>> 0;
68
+ h = Math.imul(h ^ (h >>> 13), 0xc2b2ae35) >>> 0;
69
+ return (h ^ (h >>> 16)) >>> 0;
70
+ }
71
+ function createFixedStep(H, maxSteps) {
72
+ let acc = 0;
73
+ return {
74
+ H,
75
+ run(d, step) {
76
+ acc += Math.max(d, 0);
77
+ let k = 0;
78
+ while (acc >= H && k < maxSteps) {
79
+ step(H);
80
+ acc -= H;
81
+ k++;
82
+ }
83
+ if (k === maxSteps)
84
+ acc = Math.min(acc, H);
85
+ return acc / H;
86
+ },
87
+ reset() { acc = 0; },
88
+ };
89
+ }
90
+ function createPickProxy(center, radius) {
91
+ const geo = new THREE.SphereGeometry(1, 16, 10);
92
+ const mat = new THREE.MeshBasicMaterial({ visible: false });
93
+ const mesh = new THREE.Mesh(geo, mat);
94
+ mesh.name = 'pickProxy';
95
+ mesh.position.set(center[0], center[1], center[2]);
96
+ mesh.scale.setScalar(radius);
97
+ return { mesh, dispose() { geo.dispose(); mat.dispose(); } };
98
+ }
99
+ const _frustum = new THREE.Frustum();
100
+ const _pm = new THREE.Matrix4();
101
+ const _sphere = new THREE.Sphere();
102
+ function inView(object, camera, center, radius, size) {
103
+ if (!camera || !camera.projectionMatrix)
104
+ return true;
105
+ object.updateWorldMatrix(true, false);
106
+ _sphere.center.set(center[0], center[1], center[2]).multiplyScalar(size).applyMatrix4(object.matrixWorld);
107
+ _sphere.radius = radius * size * object.matrixWorld.getMaxScaleOnAxis();
108
+ _pm.multiplyMatrices(camera.projectionMatrix, camera.matrixWorldInverse);
109
+ _frustum.setFromProjectionMatrix(_pm);
110
+ return _frustum.intersectsSphere(_sphere);
111
+ }
112
+ /** Shared GLSL for heads (a white-hot core in a coloured glow). */
113
+ const HEAD_FRAG = /* glsl */ `
114
+ varying vec3 vCol;
115
+ varying float vA;
116
+ void main() {
117
+ vec2 d = gl_PointCoord * 2.0 - 1.0;
118
+ float r2 = dot(d, d);
119
+ if (r2 > 1.0) discard;
120
+ float core = exp(-r2 * 40.0);
121
+ float glow = exp(-r2 * 8.0) * 0.5 + exp(-r2 * 2.5) * 0.1;
122
+ float a = clamp((core + glow) * (1.0 - r2) * vA, 0.0, 1.0);
123
+ if (a < 0.003) discard;
124
+ vec3 c = vCol / max(max(vCol.r, max(vCol.g, vCol.b)), 1.0);
125
+ gl_FragColor = vec4(mix(c, vec3(1.0), core * 0.9), a);
126
+ }
127
+ `;
128
+ const POINTER_MODES = ['obstacle', 'jet', 'vortex'];
129
+ const RAKES = ['tube', 'sheet', 'cross'];
130
+ const H_STEP = 1 / 90;
131
+ const U0 = 0.55; // wind speed (units / s) at flowSpeed 1
132
+ const XL0 = 1.7, YL0 = 1.15; // smallest tunnel half extents (along the wind / across)
133
+ const GX = 56, GY = 40, GZ = 40; // base-flow grid
134
+ const DELTA = 0.32; // boundary-layer thickness for the potential ramp
135
+ const TRAIL_LOOK = { streak: 0.35, comet: 1, echo: 1 };
136
+ const TRAIL_ALPHA = { streak: 1.8, comet: 2, echo: 2.6 };
137
+ const BOUNDS = { center: [0, 0, 0], radius: 1.6 };
138
+ function createUniforms() {
139
+ return {
140
+ uTime: { value: 0 },
141
+ uSize: { value: 1 },
142
+ uViewH: { value: 800 },
143
+ uIntensity: { value: 1 },
144
+ uSpeed: { value: 1 },
145
+ uOpacity: { value: 0.9 },
146
+ uColor: colorUniform('#ffffff'),
147
+ uParticleCount: { value: 0 },
148
+ uFlowSpeed: { value: 1 },
149
+ uWindPitch: { value: 0 },
150
+ uLanes: { value: 22 },
151
+ uStreamWidth: { value: 0.75 },
152
+ uTurbulence: { value: 0.6 },
153
+ uFastColor: colorUniform('#ffffff'),
154
+ uHeadSize: { value: 1 },
155
+ uPointerMode: { value: 0 },
156
+ uPointerStrength: { value: 1 },
157
+ uPointerRadius: { value: 1 },
158
+ uPointerColor: colorUniform('#ffffff'),
159
+ ...createPointerUniforms(),
160
+ ...createTrailUniforms(),
161
+ };
162
+ }
163
+ function applyConfig(u, c, size) {
164
+ u.uSize.value = size;
165
+ u.uIntensity.value = c.intensity;
166
+ u.uSpeed.value = c.speed;
167
+ u.uOpacity.value = c.opacity;
168
+ u.uColor.value.set(c.color);
169
+ u.uParticleCount.value = c.particleCount;
170
+ u.uFlowSpeed.value = c.flowSpeed;
171
+ u.uWindPitch.value = c.windPitch;
172
+ u.uLanes.value = c.lanes;
173
+ u.uStreamWidth.value = c.streamWidth;
174
+ u.uTurbulence.value = c.turbulence;
175
+ u.uFastColor.value.set(c.fastColor);
176
+ u.uHeadSize.value = c.headSize;
177
+ u.uPointerMode.value = POINTER_MODES.indexOf(c.pointerMode); // -1 = 'none' (off)
178
+ u.uPointerStrength.value = c.pointerStrength;
179
+ u.uPointerRadius.value = c.pointerRadius;
180
+ u.uPointerColor.value.set(c.pointerColor);
181
+ applyTrailConfig(u, c);
182
+ }
183
+ // code = speed ratio s = |u| / (1.8 U) (0..1) + 2 x cursor glow (0..31)
184
+ const PRESSURE_GLSL = /* glsl */ `
185
+ uniform vec3 uColor, uFastColor, uPointerColor;
186
+ vec3 pressureLight(float code) {
187
+ float glow = floor(code / 2.0) / 31.0;
188
+ float s = code - 2.0 * floor(code / 2.0);
189
+ float q = s * 1.8; // |u| / U
190
+ float cp = 1.0 - q * q; // Bernoulli pressure coefficient
191
+ float t = smoothstep(0.9, -1.4, cp); // 0 high pressure .. 1 low pressure
192
+ vec3 c = mix(uColor, uFastColor, t);
193
+ c = mix(c, vec3(1.0), 0.45 * smoothstep(-1.2, -2.2, cp)); // the fastest flow whitens
194
+ return mix(c, uPointerColor, 0.6 * glow) * (1.1 + 0.6 * t);
195
+ }
196
+ `;
197
+ const headVertex = /* glsl */ `
198
+ uniform float uSize, uViewH, uIntensity, uOpacity, uHeadSize;
199
+ ${PRESSURE_GLSL}
200
+ attribute vec2 aH; // code, fade (spawn / exit)
201
+ varying vec3 vCol;
202
+ varying float vA;
203
+ void main() {
204
+ vec4 mv = modelViewMatrix * vec4(position * uSize, 1.0);
205
+ vCol = pressureLight(aH.x) * uIntensity;
206
+ vA = uOpacity * aH.y * 0.9;
207
+ gl_PointSize = clamp(uHeadSize * uSize * uViewH * 0.014 / -mv.z, 1.5, 22.0) * step(0.01, aH.y);
208
+ gl_Position = projectionMatrix * mv;
209
+ }
210
+ `;
211
+ // smooth ramp from Bridson's paper: 0 at the surface, 1 beyond the boundary layer
212
+ function ramp(r) {
213
+ if (r >= 1)
214
+ return 1;
215
+ if (r <= 0)
216
+ return 0;
217
+ return (15 / 8) * r - (10 / 8) * r * r * r + (3 / 8) * r * r * r * r * r;
218
+ }
219
+ function build(u, c, size) {
220
+ const q = qualityScale(c.quality);
221
+ const n = Math.max(50, Math.round(c.particleCount * q));
222
+ const rng = mulberry32(seedMix(0xf10e, c.seed));
223
+ const F = shapeField(c.shape);
224
+ // the tunnel grows with the shape: a margin upstream / downstream and round the sides
225
+ const ext = Math.max(F.rMax, (F.Y1 - F.Y0) / 2);
226
+ const XL = Math.max(XL0, ext + 0.95), YL = Math.max(YL0, ext + 0.4);
227
+ const bR = Math.max(BOUNDS.radius, Math.hypot(XL, YL) * 0.95);
228
+ const pitch = (c.windPitch * Math.PI) / 180;
229
+ const Ux = Math.cos(pitch), Uy = Math.sin(pitch); // unit wind direction (in the x-y plane)
230
+ // ---- signed distance to the shape, from its radial field ----
231
+ function sdf(x, y, z) {
232
+ const r = Math.hypot(x, z), th = Math.atan2(z, x);
233
+ const hc = Math.min(Math.max(y, F.Y0), F.Y1);
234
+ const R = F.rAt(th, hc);
235
+ const dr = r - R;
236
+ const dy = y > F.Y1 ? y - F.Y1 : y < F.Y0 ? F.Y0 - y : 0;
237
+ if (dy === 0) {
238
+ if (dr >= 0)
239
+ return dr;
240
+ return Math.max(dr, y - F.Y1, F.Y0 - y); // inside: nearest wall or cap
241
+ }
242
+ return dr <= 0 ? dy : Math.hypot(dr, dy); // above or below the caps
243
+ }
244
+ // ---- base flow on a grid: u = curl psi', psi' = a psi + (1 - a) n (n . psi), psi = (U x x) / 2 ----
245
+ const dx = (2 * XL) / (GX - 1), dy = (2 * YL) / (GY - 1), dz = (2 * YL) / (GZ - 1);
246
+ const NN = GX * GY * GZ;
247
+ const D = new Float32Array(NN);
248
+ const idx = (i, j, k) => (k * GY + j) * GX + i;
249
+ const gxp = (i) => -XL + i * dx, gyp = (j) => -YL + j * dy, gzp = (k) => -YL + k * dz;
250
+ for (let k = 0; k < GZ; k++)
251
+ for (let j = 0; j < GY; j++)
252
+ for (let i = 0; i < GX; i++)
253
+ D[idx(i, j, k)] = sdf(gxp(i), gyp(j), gzp(k));
254
+ const PS = new Float32Array(NN * 3);
255
+ for (let k = 0; k < GZ; k++)
256
+ for (let j = 0; j < GY; j++)
257
+ for (let i = 0; i < GX; i++) {
258
+ const o = idx(i, j, k);
259
+ const x = gxp(i), y = gyp(j), z = gzp(k);
260
+ // psi = (U x x) / 2 with U = (Ux, Uy, 0)
261
+ let px = 0.5 * (Uy * z), py = 0.5 * (-Ux * z), pz = 0.5 * (Ux * y - Uy * x);
262
+ const d = D[o];
263
+ const a = ramp(d / DELTA);
264
+ if (a < 1) {
265
+ // normal from the distance field
266
+ const i0 = Math.max(i - 1, 0), i1 = Math.min(i + 1, GX - 1), j0 = Math.max(j - 1, 0), j1 = Math.min(j + 1, GY - 1), k0 = Math.max(k - 1, 0), k1 = Math.min(k + 1, GZ - 1);
267
+ let nx = (D[idx(i1, j, k)] - D[idx(i0, j, k)]) / ((i1 - i0) * dx);
268
+ let ny = (D[idx(i, j1, k)] - D[idx(i, j0, k)]) / ((j1 - j0) * dy);
269
+ let nz = (D[idx(i, j, k1)] - D[idx(i, j, k0)]) / ((k1 - k0) * dz);
270
+ const nl = Math.hypot(nx, ny, nz) || 1;
271
+ nx /= nl;
272
+ ny /= nl;
273
+ nz /= nl;
274
+ const pn = px * nx + py * ny + pz * nz;
275
+ px = a * px + (1 - a) * nx * pn;
276
+ py = a * py + (1 - a) * ny * pn;
277
+ pz = a * pz + (1 - a) * nz * pn;
278
+ }
279
+ PS[o * 3] = px;
280
+ PS[o * 3 + 1] = py;
281
+ PS[o * 3 + 2] = pz;
282
+ }
283
+ const V = new Float32Array(NN * 3); // unit-wind velocity field
284
+ for (let k = 0; k < GZ; k++)
285
+ for (let j = 0; j < GY; j++)
286
+ for (let i = 0; i < GX; i++) {
287
+ const o = idx(i, j, k);
288
+ const i0 = Math.max(i - 1, 0), i1 = Math.min(i + 1, GX - 1), j0 = Math.max(j - 1, 0), j1 = Math.min(j + 1, GY - 1), k0 = Math.max(k - 1, 0), k1 = Math.min(k + 1, GZ - 1);
289
+ const ddy = (c2) => (PS[idx(i, j1, k) * 3 + c2] - PS[idx(i, j0, k) * 3 + c2]) / ((j1 - j0) * dy);
290
+ const ddz = (c2) => (PS[idx(i, j, k1) * 3 + c2] - PS[idx(i, j, k0) * 3 + c2]) / ((k1 - k0) * dz);
291
+ const ddx = (c2) => (PS[idx(i1, j, k) * 3 + c2] - PS[idx(i0, j, k) * 3 + c2]) / ((i1 - i0) * dx);
292
+ V[o * 3] = ddy(2) - ddz(1);
293
+ V[o * 3 + 1] = ddz(0) - ddx(2);
294
+ V[o * 3 + 2] = ddx(1) - ddy(0);
295
+ }
296
+ const NG = new Float32Array(NN * 3); // outward normal of the distance field
297
+ for (let k = 0; k < GZ; k++)
298
+ for (let j = 0; j < GY; j++)
299
+ for (let i = 0; i < GX; i++) {
300
+ const o = idx(i, j, k);
301
+ const i0 = Math.max(i - 1, 0), i1 = Math.min(i + 1, GX - 1), j0 = Math.max(j - 1, 0), j1 = Math.min(j + 1, GY - 1), k0 = Math.max(k - 1, 0), k1 = Math.min(k + 1, GZ - 1);
302
+ let nx = (D[idx(i1, j, k)] - D[idx(i0, j, k)]) / ((i1 - i0) * dx);
303
+ let ny = (D[idx(i, j1, k)] - D[idx(i, j0, k)]) / ((j1 - j0) * dy);
304
+ let nz = (D[idx(i, j, k1)] - D[idx(i, j, k0)]) / ((k1 - k0) * dz);
305
+ const nl = Math.hypot(nx, ny, nz) || 1;
306
+ NG[o * 3] = nx / nl;
307
+ NG[o * 3 + 1] = ny / nl;
308
+ NG[o * 3 + 2] = nz / nl;
309
+ }
310
+ const W = new Float32Array(NN); // wake mask: behind the body, outside it
311
+ for (let k = 0; k < GZ; k++)
312
+ for (let j = 0; j < GY; j++)
313
+ for (let i = 0; i < GX; i++) {
314
+ const o = idx(i, j, k);
315
+ const x = gxp(i), y = gyp(j), z = gzp(k);
316
+ const along = x * Ux + y * Uy, ax = x - along * Ux, ay = y - along * Uy;
317
+ const across = Math.hypot(ax, ay, z);
318
+ const behind = Math.min(Math.max((along - 0.1) / 0.5, 0), 1);
319
+ W[o] = behind * Math.exp(-(across * across) / (0.75 * 0.75)) * ramp(D[o] / 0.25);
320
+ }
321
+ const sv = new Float32Array(8);
322
+ function sample(x, y, z) {
323
+ let fx = (x + XL) / dx, fy = (y + YL) / dy, fz = (z + YL) / dz;
324
+ if (fx < 0)
325
+ fx = 0;
326
+ else if (fx > GX - 1.001)
327
+ fx = GX - 1.001;
328
+ if (fy < 0)
329
+ fy = 0;
330
+ else if (fy > GY - 1.001)
331
+ fy = GY - 1.001;
332
+ if (fz < 0)
333
+ fz = 0;
334
+ else if (fz > GZ - 1.001)
335
+ fz = GZ - 1.001;
336
+ const i = fx | 0, j = fy | 0, k = fz | 0, tx = fx - i, ty = fy - j, tz = fz - k;
337
+ const o000 = (k * GY + j) * GX + i, o100 = o000 + 1, o010 = o000 + GX, o110 = o010 + 1;
338
+ const o001 = o000 + GX * GY, o101 = o001 + 1, o011 = o001 + GX, o111 = o011 + 1;
339
+ const w000 = (1 - tx) * (1 - ty) * (1 - tz), w100 = tx * (1 - ty) * (1 - tz), w010 = (1 - tx) * ty * (1 - tz), w110 = tx * ty * (1 - tz);
340
+ const w001 = (1 - tx) * (1 - ty) * tz, w101 = tx * (1 - ty) * tz, w011 = (1 - tx) * ty * tz, w111 = tx * ty * tz;
341
+ for (let cc = 0; cc < 3; cc++) {
342
+ sv[cc] = V[o000 * 3 + cc] * w000 + V[o100 * 3 + cc] * w100 + V[o010 * 3 + cc] * w010 + V[o110 * 3 + cc] * w110
343
+ + V[o001 * 3 + cc] * w001 + V[o101 * 3 + cc] * w101 + V[o011 * 3 + cc] * w011 + V[o111 * 3 + cc] * w111;
344
+ }
345
+ sv[3] = W[o000] * w000 + W[o100] * w100 + W[o010] * w010 + W[o110] * w110 + W[o001] * w001 + W[o101] * w101 + W[o011] * w011 + W[o111] * w111;
346
+ sv[4] = D[o000] * w000 + D[o100] * w100 + D[o010] * w010 + D[o110] * w110 + D[o001] * w001 + D[o101] * w101 + D[o011] * w011 + D[o111] * w111;
347
+ for (let cc = 0; cc < 3; cc++) {
348
+ sv[5 + cc] = NG[o000 * 3 + cc] * w000 + NG[o100 * 3 + cc] * w100 + NG[o010 * 3 + cc] * w010 + NG[o110 * 3 + cc] * w110
349
+ + NG[o001 * 3 + cc] * w001 + NG[o101 * 3 + cc] * w101 + NG[o011 * 3 + cc] * w011 + NG[o111 * 3 + cc] * w111;
350
+ }
351
+ }
352
+ // ---- tracers on a lattice of lanes upstream ----
353
+ const L = Math.max(2, Math.round(c.lanes));
354
+ const e1x = -Uy, e1y = Ux; // across the wind in the x-y plane (e2 = z)
355
+ // the rake: where the streams are released. tube = a ring of lanes round the body (the stream tube
356
+ // bulges round the shape), sheet = one vertical smoke rake, cross = a vertical and a horizontal rake
357
+ const rake = RAKES.includes(c.rake) ? c.rake : 'tube';
358
+ const laneA = new Float32Array(n), laneB = new Float32Array(n), phase = new Float32Array(n);
359
+ const perLane = Math.ceil(n / L);
360
+ for (let i = 0; i < n; i++) {
361
+ const l = i % L, k = Math.floor(i / L);
362
+ const f = (l + 0.5) / L;
363
+ if (rake === 'tube') {
364
+ laneA[i] = Math.cos(f * Math.PI * 2) * 0.62;
365
+ laneB[i] = Math.sin(f * Math.PI * 2) * 0.62;
366
+ }
367
+ else if (rake === 'sheet') {
368
+ laneA[i] = f * 2 - 1;
369
+ laneB[i] = (l % 2 ? 1 : -1) * 0.012;
370
+ } // a hair either side of the symmetry plane
371
+ else {
372
+ const g = ((l >> 1) + 0.5) / Math.ceil(L / 2) * 2 - 1;
373
+ if (l % 2 === 0) {
374
+ laneA[i] = g;
375
+ laneB[i] = 0;
376
+ }
377
+ else {
378
+ laneA[i] = 0;
379
+ laneB[i] = g;
380
+ }
381
+ }
382
+ phase[i] = (k + rng()) / perLane; // stratified along the lane, no synchronised fronts
383
+ }
384
+ const x = new Float32Array(n * 3), v = new Float32Array(n * 3), code = new Float32Array(n), fade = new Float32Array(n);
385
+ const hA = new Float32Array(n * 2), glow = new Float32Array(n);
386
+ const S0 = -XL * 0.95; // release plane, along the wind
387
+ let trail = null;
388
+ function release(i, frac) {
389
+ const w = u.uStreamWidth.value * YL * 0.95;
390
+ const a = laneA[i] * w, b = laneB[i] * w;
391
+ const along = S0 + frac * (2 * XL * 0.95);
392
+ x[i * 3] = along * Ux + a * e1x;
393
+ x[i * 3 + 1] = along * Uy + a * e1y;
394
+ x[i * 3 + 2] = b;
395
+ fade[i] = frac > 0.02 ? 1 : 0;
396
+ if (trail)
397
+ trail.reset(i);
398
+ }
399
+ let time = 0;
400
+ const P = new THREE.Vector3(), PV = new THREE.Vector3(), axis = new THREE.Vector3(0, 0, 1);
401
+ const vel = new Float32Array(3);
402
+ function velocity(px, py, pz, t, mode, S, Rp) {
403
+ sample(px, py, pz);
404
+ const Ug = U0 * u.uFlowSpeed.value;
405
+ let vx = sv[0] * Ug, vy = sv[1] * Ug, vz = sv[2] * Ug;
406
+ // skin of the body: a slip current along the surface carries tracers off the stagnation point, and
407
+ // anything that strays inside is pushed back out (tracers never pile up on the body)
408
+ const dd = sv[4];
409
+ if (dd < 0.15) {
410
+ const nx = sv[5], ny = sv[6], nz = sv[7];
411
+ if (dd < 0) {
412
+ // inside the body (only through grid leakage): straight back out
413
+ const out = Ug * (0.6 + 10 * -dd);
414
+ vx = nx * out;
415
+ vy = ny * out;
416
+ vz = nz * out;
417
+ }
418
+ else {
419
+ // impermeable skin: remove any inflow through the surface (the coarse grid leaks a little)
420
+ const vn = vx * nx + vy * ny + vz * nz;
421
+ const wgt = 1 - dd / 0.15;
422
+ if (vn < 0) {
423
+ vx -= vn * nx * wgt;
424
+ vy -= vn * ny * wgt;
425
+ vz -= vn * nz * wgt;
426
+ }
427
+ // slip current along the skin carries tracers off the stagnation point
428
+ const un = Ux * nx + Uy * ny;
429
+ let tx = Ux - un * nx, ty = Uy - un * ny, tz = -un * nz;
430
+ if (Math.hypot(tx, ty, tz) < 0.35) {
431
+ // head-on (a flat face or an edge square to the wind): go round the side the tracer is on,
432
+ // i.e. away from the wind axis through the body, so a symmetric body splits the stream both ways
433
+ const al = px * Ux + py * Uy;
434
+ let rx = px - al * Ux, ry = py - al * Uy, rz = pz;
435
+ const rn = rx * nx + ry * ny + rz * nz;
436
+ rx -= rn * nx;
437
+ ry -= rn * ny;
438
+ rz -= rn * nz;
439
+ const rl = Math.hypot(rx, ry, rz);
440
+ if (rl > 1e-4) {
441
+ tx += rx / rl * 0.8;
442
+ ty += ry / rl * 0.8;
443
+ tz += rz / rl * 0.8;
444
+ }
445
+ }
446
+ const tn = Math.hypot(tx, ty, tz) || 1;
447
+ const g = 0.6 * Ug * wgt;
448
+ vx += tx / tn * g;
449
+ vy += ty / tn * g;
450
+ vz += tz / tn * g;
451
+ if (dd < 0.03) {
452
+ const push = Ug * (0.03 - dd) * 30;
453
+ vx += nx * push;
454
+ vy += ny * push;
455
+ vz += nz * push;
456
+ }
457
+ }
458
+ }
459
+ // wake eddies: an ABC flow carried with the wind, faded in behind the body
460
+ const tb = u.uTurbulence.value * sv[3];
461
+ if (tb > 0.002) {
462
+ const kk = 4.2, ph = t * Ug * kk;
463
+ const X = px * kk - ph, Y = py * kk, Z = pz * kk;
464
+ const A = 0.55 * Ug * tb;
465
+ vx += A * (Math.sin(Z + 0.3 * ph) + Math.cos(Y));
466
+ vy += A * (Math.sin(X) + Math.cos(Z + 0.3 * ph));
467
+ vz += A * (Math.sin(Y) + Math.cos(X));
468
+ }
469
+ // the cursor
470
+ if (S > 0.001) {
471
+ let ex = px - P.x, ey = py - P.y, ez = pz - P.z;
472
+ if (mode === 0) { // a sphere in potential flow: U + (a^3/2)(U/r^3 - 3(U.x)x/r^5)
473
+ const a = 0.22 * u.uPointerRadius.value * Math.min(S, 2);
474
+ const r2 = ex * ex + ey * ey + ez * ez, r = Math.sqrt(r2) + 1e-4;
475
+ if (r < 5 * a) {
476
+ const ua = Ug * Ux, ub = Ug * Uy;
477
+ const ud = ua * ex + ub * ey;
478
+ const k3 = (a * a * a) / 2 / (r2 * r);
479
+ vx += k3 * (ua - 3 * ud * ex / r2);
480
+ vy += k3 * (ub - 3 * ud * ey / r2);
481
+ vz += k3 * (-3 * ud * ez / r2);
482
+ if (r < a * 1.02) {
483
+ vx += ex / r * Ug * 2;
484
+ vy += ey / r * Ug * 2;
485
+ vz += ez / r * Ug * 2;
486
+ } // never inside
487
+ }
488
+ }
489
+ else {
490
+ const al = ex * axis.x + ey * axis.y + ez * axis.z;
491
+ ex -= axis.x * al;
492
+ ey -= axis.y * al;
493
+ ez -= axis.z * al;
494
+ const d2 = ex * ex + ey * ey + ez * ez;
495
+ if (d2 < 9 * Rp * Rp) {
496
+ const g = Math.exp(-d2 / (Rp * Rp));
497
+ if (mode === 1) { // a puff along the cursor's motion
498
+ vx += PV.x * 1.6 * S * g;
499
+ vy += PV.y * 1.6 * S * g;
500
+ vz += PV.z * 1.6 * S * g;
501
+ }
502
+ else { // line vortex (Rankine-softened)
503
+ const G = 0.5 * S * Ug / (d2 / (Rp * Rp) + 0.15) * Math.min(1, 3 * g + 0.2);
504
+ vx += (axis.y * ez - axis.z * ey) * G / Rp;
505
+ vy += (axis.z * ex - axis.x * ez) * G / Rp;
506
+ vz += (axis.x * ey - axis.y * ex) * G / Rp;
507
+ }
508
+ }
509
+ }
510
+ }
511
+ vel[0] = vx;
512
+ vel[1] = vy;
513
+ vel[2] = vz;
514
+ }
515
+ function step(dt) {
516
+ time += dt;
517
+ const mode = u.uPointerMode.value;
518
+ const S = u.uPointerStrength.value * u.uPointerActive.value;
519
+ const Rp = 0.3 * u.uPointerRadius.value;
520
+ P.copy(u.uPointer.value);
521
+ PV.copy(u.uPointerVel.value);
522
+ const Ug = Math.max(U0 * u.uFlowSpeed.value, 1e-4);
523
+ for (let i = 0; i < n; i++) {
524
+ const j = i * 3;
525
+ const px = x[j], py = x[j + 1], pz = x[j + 2];
526
+ // RK2 (midpoint)
527
+ velocity(px, py, pz, time, mode, S, Rp);
528
+ const mx = px + vel[0] * dt * 0.5, my = py + vel[1] * dt * 0.5, mz = pz + vel[2] * dt * 0.5;
529
+ velocity(mx, my, mz, time + dt * 0.5, mode, S, Rp);
530
+ let nx = px + vel[0] * dt, ny = py + vel[1] * dt, nz = pz + vel[2] * dt;
531
+ v[j] = vel[0];
532
+ v[j + 1] = vel[1];
533
+ v[j + 2] = vel[2];
534
+ const along = nx * Ux + ny * Uy;
535
+ if (along > XL * 0.97 || Math.abs(nz) > YL || Math.abs(-nx * Uy + ny * Ux) > YL * 1.05) {
536
+ release(i, 0); // back to its lane at the release plane
537
+ continue;
538
+ }
539
+ x[j] = nx;
540
+ x[j + 1] = ny;
541
+ x[j + 2] = nz;
542
+ // fade in after release, out before the exit
543
+ const inF = Math.min((along - S0) / 0.25, 1), outF = Math.min((XL * 0.97 - along) / 0.35, 1);
544
+ fade[i] = Math.max(Math.min(inF, outF), 0);
545
+ // glow from the cursor (how much it is being pushed)
546
+ let gl = 0;
547
+ if (S > 0.001) {
548
+ const ex = nx - P.x, ey = ny - P.y, ez = nz - P.z;
549
+ gl = Math.exp(-(ex * ex + ey * ey + ez * ez) / (Rp * Rp * 1.5));
550
+ }
551
+ glow[i] += (gl - glow[i]) * Math.min(1, dt * 5);
552
+ const s = Math.min(Math.hypot(vel[0], vel[1], vel[2]) / (1.8 * Ug), 0.999);
553
+ code[i] = s + 2 * Math.round(Math.min(glow[i], 1) * 31);
554
+ hA[i * 2] = code[i];
555
+ hA[i * 2 + 1] = fade[i];
556
+ }
557
+ }
558
+ const hgeo = new THREE.BufferGeometry();
559
+ const xAttr = new THREE.BufferAttribute(x, 3).setUsage(THREE.DynamicDrawUsage);
560
+ const hAttr = new THREE.BufferAttribute(hA, 2).setUsage(THREE.DynamicDrawUsage);
561
+ hgeo.setAttribute('position', xAttr);
562
+ hgeo.setAttribute('aH', hAttr);
563
+ const hmat = new THREE.ShaderMaterial({
564
+ uniforms: u, vertexShader: headVertex, fragmentShader: HEAD_FRAG,
565
+ transparent: true, depthWrite: false, blending: THREE.AdditiveBlending,
566
+ });
567
+ const heads = new THREE.Points(hgeo, hmat);
568
+ heads.frustumCulled = false;
569
+ heads.renderOrder = 3;
570
+ attachViewH(heads, u);
571
+ const object = new THREE.Group();
572
+ const proxy = createPickProxy(BOUNDS.center, bR);
573
+ object.add(heads, proxy.mesh);
574
+ // streaklines carry the pressure colour; the fade (spawn / exit) is packed as brightness in k
575
+ const tk = new Float32Array(n);
576
+ const trailGLSL = /* glsl */ `
577
+ ${PRESSURE_GLSL}
578
+ vec3 trailShade(vec3 p, float f) {
579
+ float lvl = floor(TRAIL_K / 64.0);
580
+ vec3 c = pressureLight(TRAIL_K - 64.0 * lvl);
581
+ c /= max(max(c.r, max(c.g, c.b)), 1.0);
582
+ return mix(c, uTrailColor, smoothstep(0.0, 0.7, f)) * (lvl / 15.0);
583
+ }
584
+ vec3 trailView(vec3 mv, out float mag) { mag = 1.0; return mv; }
585
+ `;
586
+ let trailKey = '', look = 1;
587
+ const materials = [hmat];
588
+ function buildTrails(mode, share) {
589
+ look = TRAIL_LOOK[mode] || 1;
590
+ const key = mode + ':' + share;
591
+ if (key === trailKey)
592
+ return;
593
+ trailKey = key;
594
+ if (trail) {
595
+ object.remove(trail.object);
596
+ trail.dispose();
597
+ trail = null;
598
+ }
599
+ materials.length = 1;
600
+ trail = createCpuTrail(mode, { u, n, pos: x, vel: v, k: tk, glsl: trailGLSL, sizePx: 0.01, spacing: 0.0015, sub: 8, alpha: TRAIL_ALPHA[mode] });
601
+ if (!trail)
602
+ return;
603
+ trail.object.renderOrder = 2;
604
+ object.add(trail.object);
605
+ materials.push(...trail.materials);
606
+ }
607
+ buildTrails(c.trailMode, c.trailShare);
608
+ function packTrails() {
609
+ for (let i = 0; i < n; i++)
610
+ tk[i] = Math.min(code[i], 63.9) + 64 * Math.round(fade[i] * 15);
611
+ }
612
+ // steady state from the start: every tracer is released at its lane and carried along its own
613
+ // streamline for its phase of the crossing time (coarse steps, no cursor)
614
+ {
615
+ const Ug = Math.max(U0 * u.uFlowSpeed.value, 1e-3);
616
+ const cross = (2 * XL * 0.95) / Ug;
617
+ const hs = 0.05;
618
+ for (let i = 0; i < n; i++) {
619
+ release(i, 0);
620
+ const j = i * 3;
621
+ const steps = Math.round((phase[i] * cross) / hs);
622
+ let t0 = 0;
623
+ for (let s2 = 0; s2 < steps; s2++) {
624
+ velocity(x[j], x[j + 1], x[j + 2], t0, -1, 0, 1);
625
+ const mx = x[j] + vel[0] * hs * 0.5, my = x[j + 1] + vel[1] * hs * 0.5, mz = x[j + 2] + vel[2] * hs * 0.5;
626
+ velocity(mx, my, mz, t0 + hs * 0.5, -1, 0, 1);
627
+ x[j] += vel[0] * hs;
628
+ x[j + 1] += vel[1] * hs;
629
+ x[j + 2] += vel[2] * hs;
630
+ t0 += hs;
631
+ if (x[j] * Ux + x[j + 1] * Uy > XL * 0.9)
632
+ break;
633
+ }
634
+ }
635
+ time = 0;
636
+ }
637
+ const stepper = createFixedStep(H_STEP, 6);
638
+ for (let s = 0; s < 45; s++)
639
+ step(H_STEP);
640
+ packTrails();
641
+ const invWorld = new THREE.Matrix4();
642
+ return {
643
+ object,
644
+ materials,
645
+ apply(cfg) { if (cfg)
646
+ buildTrails(cfg.trailMode, cfg.trailShare); },
647
+ update(dt, camera, pointer) {
648
+ const rdt = Math.min(Math.max(dt, 0), 1 / 20);
649
+ if (camera && !inView(object, camera, BOUNDS.center, bR, u.uSize.value))
650
+ return;
651
+ const d = rdt * u.uSpeed.value;
652
+ u.uTime.value += d;
653
+ if (camera) {
654
+ camera.getWorldDirection(axis);
655
+ axis.transformDirection(invWorld.copy(object.matrixWorld).invert()).normalize();
656
+ if (pointer)
657
+ stepPointerField(u, pointer, camera, object, u.uSize.value, rdt);
658
+ }
659
+ u.uVelScale.value = look;
660
+ let simD = 0;
661
+ stepper.run(d, (hh) => { step(hh); simD += hh; });
662
+ if (simD > 0) {
663
+ packTrails();
664
+ xAttr.needsUpdate = true;
665
+ hAttr.needsUpdate = true;
666
+ if (trail)
667
+ trail.update(simD / look);
668
+ }
669
+ },
670
+ seek(tt) { for (let s = 0; s < Math.round(tt / H_STEP); s++)
671
+ step(H_STEP); packTrails(); xAttr.needsUpdate = true; hAttr.needsUpdate = true; },
672
+ dispose() { hgeo.dispose(); hmat.dispose(); proxy.dispose(); if (trail)
673
+ trail.dispose(); },
674
+ _state: { x, code, V, D },
675
+ };
676
+ }
677
+ /** Defaults for every knob, so an older saved config still renders (identical to the catalog entry). */
678
+ const DEFAULTS = {
679
+ intensity: 1,
680
+ speed: 1,
681
+ opacity: 0.9,
682
+ size: 1,
683
+ color: '#3f7bff',
684
+ particleCount: 2400,
685
+ shape: { type: 'sphere', radius: 0.5, segments: 32, rings: 32 },
686
+ flowSpeed: 1,
687
+ windPitch: 0,
688
+ rake: 'sheet',
689
+ lanes: 44,
690
+ streamWidth: 0.85,
691
+ turbulence: 0.9,
692
+ fastColor: '#ff6a3d',
693
+ headSize: 1,
694
+ seed: 1,
695
+ quality: 'medium',
696
+ pointerMode: 'obstacle',
697
+ pointerStrength: 1,
698
+ pointerRadius: 1,
699
+ pointerColor: '#ffffff',
700
+ trailMode: 'comet',
701
+ trailLength: 1.2,
702
+ trailOpacity: 0.7,
703
+ trailColor: '#1b2a6b',
704
+ trailShare: 1,
705
+ };
706
+ /** Knobs that rebuild the simulation: they change on commit, never through the live path. */
707
+ const STRUCTURAL = ['particleCount', 'shape', 'rake', 'lanes', 'windPitch', 'seed', 'quality'];
708
+ /** Knobs an animation (or mouse move) may drive per frame — generated from applyConfig. */
709
+ const ANIMATABLE = new Set(GENERATIVE_PARTICLES_ANIMATABLE.shapeFlow.map((p) => p.value));
710
+ const ShapeFlowParticles = ({ id, size, config, animations, mouseMove, onObjectReady, onObjectDispose }) => {
711
+ const rootRef = useRef(null);
712
+ useObjectReady(rootRef, config, onObjectReady, onObjectDispose);
713
+ const s = size > 0 ? size : 1;
714
+ const cfg = useMemo(() => ({ ...DEFAULTS, ...config }), [config]);
715
+ // the shape is an object: rebuild on a change of its content, not of its identity
716
+ const shapeKey = JSON.stringify(cfg.shape);
717
+ // uniforms outlive the objects, so keyframe animations survive a rebuild
718
+ const uniforms = useMemo(() => createUniforms(), []);
719
+ // rebuilt only when a structural knob changes (trails rebuild inside apply())
720
+ const instance = useMemo(() => build(uniforms, cfg, s), [uniforms, cfg.particleCount, cfg.rake, cfg.lanes, cfg.windPitch, cfg.seed, cfg.quality, shapeKey]);
721
+ useEffect(() => () => instance.dispose(), [instance]);
722
+ useLayoutEffect(() => {
723
+ applyConfig(uniforms, cfg, s);
724
+ instance.apply(cfg);
725
+ }, [instance, uniforms, cfg, s]);
726
+ // Slider drags and keyframe animations are both overrides on the committed config.
727
+ // This is the one place they are merged and pushed, so they compose instead of
728
+ // overwriting each other; the animation wins, because it is the active driver.
729
+ const keyframes = animations?.particles?.animations;
730
+ const animOverride = useRef({});
731
+ const animFrom = useRef({});
732
+ const animStart = useRef(0);
733
+ // Editing a keyframe restarts its cycle rather than dropping the user mid-way.
734
+ useEffect(() => { animStart.current = performance.now(); animFrom.current = {}; }, [keyframes]);
735
+ const push = useCallback((overrides) => {
736
+ const merged = { ...cfg, ...overrides, ...animOverride.current };
737
+ const z = merged.size;
738
+ applyConfig(uniforms, merged, z && z > 0 ? z : s);
739
+ }, [cfg, uniforms, s]);
740
+ const live = useConfigLiveHandle(rootRef, id, 'particles', cfg, STRUCTURAL, push);
741
+ const pointer = usePointerField();
742
+ useFrame((state, delta) => {
743
+ instance.update(Math.min(delta, 0.1), state.camera, pointer);
744
+ // Keyframes first, pointer on top: a knob bound to both follows the cursor.
745
+ const pointerBound = !!mouseMove?.enabled && !!mouseMove.properties?.length;
746
+ if (keyframes?.length || pointerBound) {
747
+ applyConfigKeyframeAnimations(keyframes, animFrom.current, cfg, animOverride.current, performance.now() - animStart.current, ANIMATABLE);
748
+ if (pointerBound)
749
+ applyConfigMouseMove(mouseMove.properties, cfg, animOverride.current, state.pointer, ANIMATABLE);
750
+ push(live.current);
751
+ }
752
+ });
753
+ return (_jsx("group", { ref: rootRef, children: _jsx("primitive", { object: instance.object }) }));
754
+ };
755
+ export default ShapeFlowParticles;