@woosh/meep-engine 3.45.0 → 3.47.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 (435) hide show
  1. package/build/bundle-worker-terrain.js +1 -1
  2. package/editor/actions/concrete/TransformModifyAction.d.ts.map +1 -1
  3. package/editor/actions/concrete/TransformModifyAction.js +10 -2
  4. package/editor/ecs/component/FieldDescriptor.js +15 -0
  5. package/editor/ecs/component/createObjectEditor.js +41 -12
  6. package/editor/ecs/component/editors/ecs/Transform64Editor.d.ts.map +1 -1
  7. package/editor/ecs/component/editors/ecs/Transform64Editor.js +77 -70
  8. package/editor/tools/TransformToolV2.d.ts.map +1 -1
  9. package/editor/tools/TransformToolV2.js +4 -0
  10. package/editor/tools/v2/TransformControls.d.ts.map +1 -1
  11. package/editor/tools/v2/TransformControls.js +7 -0
  12. package/editor/view/ecs/EntityEditor.d.ts.map +1 -1
  13. package/editor/view/ecs/EntityEditor.js +4 -2
  14. package/package.json +1 -1
  15. package/src/core/assert.d.ts.map +1 -1
  16. package/src/core/assert.js +5 -1
  17. package/src/core/binary/hash/XXH128Hash.d.ts +1 -37
  18. package/src/core/binary/hash/XXH128Hash.d.ts.map +1 -1
  19. package/src/core/binary/hash/XXH128Hash.js +4 -55
  20. package/src/core/binary/hash/XXH3_SECRET.d.ts +1 -12
  21. package/src/core/binary/hash/XXH3_SECRET.d.ts.map +1 -1
  22. package/src/core/binary/hash/XXH3_SECRET.js +4 -25
  23. package/src/core/binary/hash/crc32.d.ts +1 -15
  24. package/src/core/binary/hash/crc32.d.ts.map +1 -1
  25. package/src/core/binary/hash/crc32.js +4 -96
  26. package/src/core/binary/hash/xxh3_128.d.ts +1 -9
  27. package/src/core/binary/hash/xxh3_128.d.ts.map +1 -1
  28. package/src/core/binary/hash/xxh3_128.js +4 -341
  29. package/src/core/binary/hash/xxh3_64.d.ts +1 -8
  30. package/src/core/binary/hash/xxh3_64.d.ts.map +1 -1
  31. package/src/core/binary/hash/xxh3_64.js +4 -241
  32. package/src/core/binary/hash/xxh3_common.d.ts +1 -223
  33. package/src/core/binary/hash/xxh3_common.d.ts.map +1 -1
  34. package/src/core/binary/hash/xxh3_common.js +90 -476
  35. package/src/core/collection/array/array_insert_at.d.ts +16 -0
  36. package/src/core/collection/array/array_insert_at.d.ts.map +1 -0
  37. package/src/core/collection/array/array_insert_at.js +32 -0
  38. package/src/core/collection/array/array_remove_at.d.ts +15 -0
  39. package/src/core/collection/array/array_remove_at.d.ts.map +1 -0
  40. package/src/core/collection/array/array_remove_at.js +30 -0
  41. package/src/core/collection/array/combine_hash.d.ts +6 -0
  42. package/src/core/collection/array/combine_hash.d.ts.map +1 -1
  43. package/src/core/collection/array/combine_hash.js +6 -0
  44. package/src/core/function/FunctionCompiler.js +2 -2
  45. package/src/core/geom/3d/mat4/m4_multiply.d.ts +3 -0
  46. package/src/core/geom/3d/mat4/m4_multiply.d.ts.map +1 -1
  47. package/src/core/geom/3d/mat4/m4_multiply.js +3 -0
  48. package/src/core/geom/3d/mat4/m4_multiply_f64.d.ts +30 -0
  49. package/src/core/geom/3d/mat4/m4_multiply_f64.d.ts.map +1 -0
  50. package/src/core/geom/3d/mat4/m4_multiply_f64.js +106 -0
  51. package/src/core/geom/3d/quaternion/quat3_look_rotation.d.ts +37 -0
  52. package/src/core/geom/3d/quaternion/quat3_look_rotation.d.ts.map +1 -0
  53. package/src/core/geom/3d/quaternion/quat3_look_rotation.js +172 -0
  54. package/src/core/geom/ConicRay.js +2 -2
  55. package/src/core/geom/Quaternion.d.ts +1 -0
  56. package/src/core/geom/Quaternion.d.ts.map +1 -1
  57. package/src/core/geom/Quaternion.js +12 -48
  58. package/src/core/geom/Vector4.d.ts.map +1 -1
  59. package/src/core/geom/Vector4.js +8 -5
  60. package/src/core/math/hash/XXH128Hash.d.ts +38 -0
  61. package/src/core/math/hash/XXH128Hash.d.ts.map +1 -0
  62. package/src/core/math/hash/XXH128Hash.js +55 -0
  63. package/src/core/math/hash/XXH3_SECRET.d.ts +13 -0
  64. package/src/core/math/hash/XXH3_SECRET.d.ts.map +1 -0
  65. package/src/core/math/hash/XXH3_SECRET.js +25 -0
  66. package/src/core/math/hash/crc32.d.ts +16 -0
  67. package/src/core/math/hash/crc32.d.ts.map +1 -0
  68. package/src/core/math/hash/crc32.js +96 -0
  69. package/src/core/math/hash/xxh3_128.d.ts +10 -0
  70. package/src/core/math/hash/xxh3_128.d.ts.map +1 -0
  71. package/src/core/math/hash/xxh3_128.js +341 -0
  72. package/src/core/math/hash/xxh3_64.d.ts +9 -0
  73. package/src/core/math/hash/xxh3_64.d.ts.map +1 -0
  74. package/src/core/math/hash/xxh3_64.js +241 -0
  75. package/src/core/math/hash/xxh3_common.d.ts +224 -0
  76. package/src/core/math/hash/xxh3_common.d.ts.map +1 -0
  77. package/src/core/math/hash/xxh3_common.js +476 -0
  78. package/src/core/math/lookup/ParameterLookupTable.js +2 -2
  79. package/src/core/model/node-graph/node/NodeInstancePortReference.js +2 -2
  80. package/src/core/model/reactive/model/ReactiveBinaryExpression.js +2 -2
  81. package/src/core/model/reactive/model/terminal/ReactiveReference.js +2 -2
  82. package/src/engine/Engine.d.ts.map +1 -1
  83. package/src/engine/Engine.js +9 -4
  84. package/src/engine/asset/AssetDescription.js +2 -2
  85. package/src/engine/ecs/animation/Animation.js +2 -2
  86. package/src/engine/ecs/animation/AnimationClip.d.ts.map +1 -1
  87. package/src/engine/ecs/animation/AnimationClip.js +7 -5
  88. package/src/engine/ecs/gui/GUIElement.d.ts.map +1 -1
  89. package/src/engine/ecs/gui/GUIElement.js +7 -5
  90. package/src/engine/ecs/gui/hud/HeadsUpDisplay.js +2 -2
  91. package/src/engine/ecs/gui/position/ViewportPosition.d.ts.map +1 -1
  92. package/src/engine/ecs/gui/position/ViewportPosition.js +11 -7
  93. package/src/engine/ecs/storage/populateEngineSerializationRegistry.d.ts.map +1 -1
  94. package/src/engine/ecs/storage/populateEngineSerializationRegistry.js +10 -0
  95. package/src/engine/ecs/transform/Transform64.d.ts +1 -1
  96. package/src/engine/ecs/transform/Transform64.d.ts.map +1 -1
  97. package/src/engine/ecs/transform/Transform64.js +5 -4
  98. package/src/engine/ecs/transform/t64_look_rotation.d.ts +4 -4
  99. package/src/engine/ecs/transform/t64_look_rotation.d.ts.map +1 -1
  100. package/src/engine/ecs/transform/t64_look_rotation.js +7 -18
  101. package/src/engine/graphics/ecs/animation/animator/AnimationClip.d.ts.map +1 -1
  102. package/src/engine/graphics/ecs/animation/animator/AnimationClip.js +8 -5
  103. package/src/engine/graphics/ecs/animation/animator/AnimationClipDefinition.js +2 -2
  104. package/src/engine/graphics/ecs/animation/animator/AnimationNotification.js +2 -2
  105. package/src/engine/graphics/ecs/animation/animator/AnimationNotificationDefinition.js +2 -2
  106. package/src/engine/graphics/ecs/animation/animator/graph/definition/AnimationGraphDefinition.js +2 -2
  107. package/src/engine/graphics/ecs/animation/animator/graph/definition/AnimationStateDefinition.js +2 -2
  108. package/src/engine/graphics/ecs/animation/animator/graph/definition/AnimationTransitionDefinition.d.ts.map +1 -1
  109. package/src/engine/graphics/ecs/animation/animator/graph/definition/AnimationTransitionDefinition.js +8 -5
  110. package/src/engine/graphics/ecs/camera/topdown/TopDownCameraControllerSystem.d.ts.map +1 -1
  111. package/src/engine/graphics/ecs/camera/topdown/TopDownCameraControllerSystem.js +30 -1
  112. package/src/engine/graphics/ecs/decal/v2/Decal.d.ts.map +1 -1
  113. package/src/engine/graphics/ecs/decal/v2/Decal.js +9 -8
  114. package/src/engine/graphics/render/frame_graph/resource/TextureResourceDescriptor.d.ts.map +1 -1
  115. package/src/engine/graphics/render/frame_graph/resource/TextureResourceDescriptor.js +9 -6
  116. package/src/engine/graphics3/GPUParticleEmitterSystem.d.ts +6 -0
  117. package/src/engine/graphics3/GPUParticleEmitterSystem.d.ts.map +1 -1
  118. package/src/engine/graphics3/GPUParticleEmitterSystem.js +72 -29
  119. package/src/engine/graphics3/ParticipatingMedia.js +204 -204
  120. package/src/engine/graphics3/animation/AnimationClips.d.ts +5 -0
  121. package/src/engine/graphics3/animation/AnimationClips.d.ts.map +1 -1
  122. package/src/engine/graphics3/animation/AnimationClips.js +5 -0
  123. package/src/engine/grid/obstacle/GridObstacle.js +2 -2
  124. package/src/engine/input/devices/KeyboardDevice.d.ts +1 -0
  125. package/src/engine/input/devices/KeyboardDevice.d.ts.map +1 -1
  126. package/src/engine/input/devices/KeyboardDevice.js +7 -6
  127. package/src/engine/intelligence/behavior/selector/WeightedElement.js +2 -2
  128. package/src/engine/interpolation/Interpolated.js +2 -2
  129. package/src/engine/navigation/ecs/path_following/PathFollowingSystem.d.ts.map +1 -1
  130. package/src/engine/navigation/ecs/path_following/PathFollowingSystem.js +15 -2
  131. package/src/engine/network/CONGESTION_CONTROL.md +9 -9
  132. package/src/engine/network/MESSAGE_TRANSPORT.md +364 -0
  133. package/src/engine/network/NetworkSession.d.ts +31 -11
  134. package/src/engine/network/NetworkSession.d.ts.map +1 -1
  135. package/src/engine/network/NetworkSession.js +453 -286
  136. package/src/engine/network/README.md +77 -27
  137. package/src/engine/network/SMOOTHNESS_DESIGN.md +13 -5
  138. package/src/engine/network/diagnostics/BandwidthMeter.d.ts +1 -1
  139. package/src/engine/network/diagnostics/BandwidthMeter.js +1 -1
  140. package/src/engine/network/orchestrator/HostJoin.d.ts +111 -0
  141. package/src/engine/network/orchestrator/HostJoin.d.ts.map +1 -0
  142. package/src/engine/network/orchestrator/HostJoin.js +271 -0
  143. package/src/engine/network/orchestrator/NetworkPeer.d.ts +151 -112
  144. package/src/engine/network/orchestrator/NetworkPeer.d.ts.map +1 -1
  145. package/src/engine/network/orchestrator/NetworkPeer.js +450 -499
  146. package/src/engine/network/orchestrator/PendingSlices.d.ts +30 -0
  147. package/src/engine/network/orchestrator/PendingSlices.d.ts.map +1 -0
  148. package/src/engine/network/orchestrator/PendingSlices.js +83 -0
  149. package/src/engine/network/orchestrator/ReliableFrames.d.ts +34 -0
  150. package/src/engine/network/orchestrator/ReliableFrames.d.ts.map +1 -0
  151. package/src/engine/network/orchestrator/ReliableFrames.js +96 -0
  152. package/src/engine/network/orchestrator/ServerAuthoritativeClient.d.ts +77 -10
  153. package/src/engine/network/orchestrator/ServerAuthoritativeClient.d.ts.map +1 -1
  154. package/src/engine/network/orchestrator/ServerAuthoritativeClient.js +236 -61
  155. package/src/engine/network/orchestrator/ServerAuthoritativeServer.d.ts +20 -6
  156. package/src/engine/network/orchestrator/ServerAuthoritativeServer.d.ts.map +1 -1
  157. package/src/engine/network/orchestrator/ServerAuthoritativeServer.js +33 -8
  158. package/src/engine/network/replication/Replicator.d.ts.map +1 -1
  159. package/src/engine/network/replication/Replicator.js +7 -1
  160. package/src/engine/network/sim/ActionLog.d.ts +32 -5
  161. package/src/engine/network/sim/ActionLog.d.ts.map +1 -1
  162. package/src/engine/network/sim/ActionLog.js +47 -5
  163. package/src/engine/network/sim/SimActionExecutor.d.ts +42 -2
  164. package/src/engine/network/sim/SimActionExecutor.d.ts.map +1 -1
  165. package/src/engine/network/sim/SimActionExecutor.js +100 -4
  166. package/src/engine/network/sim/Snapshotter.d.ts +12 -0
  167. package/src/engine/network/sim/Snapshotter.d.ts.map +1 -1
  168. package/src/engine/network/sim/Snapshotter.js +43 -0
  169. package/src/engine/network/state/Baseline.d.ts +1 -1
  170. package/src/engine/network/state/Baseline.js +1 -1
  171. package/src/engine/network/state/FrameBufferRing.d.ts +25 -6
  172. package/src/engine/network/state/FrameBufferRing.d.ts.map +1 -1
  173. package/src/engine/network/state/FrameBufferRing.js +51 -6
  174. package/src/engine/network/state/InputRing.d.ts +4 -0
  175. package/src/engine/network/state/InputRing.d.ts.map +1 -1
  176. package/src/engine/network/state/InputRing.js +7 -0
  177. package/src/engine/network/transport/DeferredTransport.d.ts.map +1 -1
  178. package/src/engine/network/transport/DeferredTransport.js +1 -0
  179. package/src/engine/network/transport/LoopbackTransport.d.ts.map +1 -1
  180. package/src/engine/network/transport/LoopbackTransport.js +4 -2
  181. package/src/engine/network/transport/Transport.d.ts +7 -0
  182. package/src/engine/network/transport/Transport.d.ts.map +1 -1
  183. package/src/engine/network/transport/Transport.js +8 -0
  184. package/src/engine/network/transport/adapters/NodeUDPTransport.d.ts.map +1 -1
  185. package/src/engine/network/transport/adapters/NodeUDPTransport.js +20 -5
  186. package/src/engine/network/transport/adapters/WebRTCDataChannelTransport.d.ts.map +1 -1
  187. package/src/engine/network/transport/adapters/WebRTCDataChannelTransport.js +8 -0
  188. package/src/engine/network/transport/adapters/WebTransportTransport.d.ts.map +1 -1
  189. package/src/engine/network/transport/adapters/WebTransportTransport.js +6 -0
  190. package/src/engine/network/transport/connection/Connection.d.ts +191 -0
  191. package/src/engine/network/transport/connection/Connection.d.ts.map +1 -0
  192. package/src/engine/network/transport/connection/Connection.js +1262 -0
  193. package/src/engine/network/transport/connection/RangeSet.d.ts +94 -0
  194. package/src/engine/network/transport/connection/RangeSet.d.ts.map +1 -0
  195. package/src/engine/network/transport/connection/RangeSet.js +260 -0
  196. package/src/engine/network/transport/connection/RxStream.d.ts +48 -0
  197. package/src/engine/network/transport/connection/RxStream.d.ts.map +1 -0
  198. package/src/engine/network/transport/connection/RxStream.js +211 -0
  199. package/src/engine/network/transport/connection/TxStream.d.ts +90 -0
  200. package/src/engine/network/transport/connection/TxStream.d.ts.map +1 -0
  201. package/src/engine/network/transport/connection/TxStream.js +243 -0
  202. package/src/engine/network/transport/connection/bytes_copy.d.ts +17 -0
  203. package/src/engine/network/transport/connection/bytes_copy.d.ts.map +1 -0
  204. package/src/engine/network/transport/connection/bytes_copy.js +34 -0
  205. package/src/engine/network/transport/connection/varint.d.ts +46 -0
  206. package/src/engine/network/transport/connection/varint.d.ts.map +1 -0
  207. package/src/engine/network/transport/connection/varint.js +107 -0
  208. package/src/engine/physics/cloth/ecs/Cloth.d.ts.map +1 -1
  209. package/src/engine/physics/cloth/ecs/Cloth.js +7 -5
  210. package/src/engine/physics/cloth/ecs/ClothCollider.d.ts.map +1 -1
  211. package/src/engine/physics/cloth/ecs/ClothCollider.js +7 -5
  212. package/src/engine/physics/cloth/ecs/ClothDynamics.d.ts.map +1 -1
  213. package/src/engine/physics/cloth/ecs/ClothDynamics.js +20 -11
  214. package/src/engine/physics/fluid/FluidField.d.ts.map +1 -1
  215. package/src/engine/physics/fluid/FluidField.js +7 -5
  216. package/src/engine/physics/fluid/ecs/FluidComponent.d.ts.map +1 -1
  217. package/src/engine/physics/fluid/ecs/FluidComponent.js +19 -11
  218. package/src/engine/physics/fluid/ecs/FluidObstacleSystem.d.ts +4 -4
  219. package/src/engine/physics/fluid/effector/AbstractFluidEffector.d.ts +2 -2
  220. package/src/engine/physics/fluid/effector/AbstractFluidEffector.js +2 -2
  221. package/src/engine/physics/fluid/effector/GlobalFluidEffector.d.ts.map +1 -1
  222. package/src/engine/physics/fluid/effector/GlobalFluidEffector.js +11 -7
  223. package/src/engine/physics/fluid/effector/ImpulseFluidEffector.d.ts.map +1 -1
  224. package/src/engine/physics/fluid/effector/ImpulseFluidEffector.js +11 -7
  225. package/src/engine/physics/fluid/effector/WakeFluidEffector.d.ts.map +1 -1
  226. package/src/engine/physics/fluid/effector/WakeFluidEffector.js +16 -9
  227. package/src/engine/sound/ecs/audio/AudioEmitter.d.ts +38 -7
  228. package/src/engine/sound/ecs/audio/AudioEmitter.d.ts.map +1 -1
  229. package/src/engine/sound/ecs/audio/AudioEmitter.js +47 -14
  230. package/src/engine/sound/ecs/audio/AudioEmitterSerializationAdapter.d.ts.map +1 -1
  231. package/src/engine/sound/ecs/audio/AudioEmitterSerializationAdapter.js +5 -1
  232. package/src/engine/sound/ecs/audio/AudioEmitterSerializationUpgrader_0_1.d.ts +18 -0
  233. package/src/engine/sound/ecs/audio/AudioEmitterSerializationUpgrader_0_1.d.ts.map +1 -0
  234. package/src/engine/sound/ecs/audio/AudioEmitterSerializationUpgrader_0_1.js +48 -0
  235. package/src/engine/sound/ecs/audio/AudioEmitterSystem.d.ts +12 -2
  236. package/src/engine/sound/ecs/audio/AudioEmitterSystem.d.ts.map +1 -1
  237. package/src/engine/sound/ecs/audio/AudioEmitterSystem.js +173 -9
  238. package/src/engine/sound/ecs/audio/LiveEmitterSet.d.ts +9 -3
  239. package/src/engine/sound/ecs/audio/LiveEmitterSet.d.ts.map +1 -1
  240. package/src/engine/sound/ecs/audio/LiveEmitterSet.js +28 -8
  241. package/src/engine/sound/ecs/trigger/AudioEventTrigger.d.ts +8 -0
  242. package/src/engine/sound/ecs/trigger/AudioEventTrigger.d.ts.map +1 -1
  243. package/src/engine/sound/ecs/trigger/AudioEventTrigger.js +192 -191
  244. package/src/engine/sound/ecs/trigger/AudioEventTriggerSerializationAdapter.d.ts.map +1 -1
  245. package/src/engine/sound/ecs/trigger/AudioEventTriggerSerializationAdapter.js +5 -1
  246. package/src/engine/sound/ecs/trigger/AudioEventTriggerSerializationUpgrader_0_1.d.ts +18 -0
  247. package/src/engine/sound/ecs/trigger/AudioEventTriggerSerializationUpgrader_0_1.d.ts.map +1 -0
  248. package/src/engine/sound/ecs/trigger/AudioEventTriggerSerializationUpgrader_0_1.js +51 -0
  249. package/src/engine/sound/ecs/trigger/AudioEventTriggerSystem.d.ts.map +1 -1
  250. package/src/engine/sound/ecs/trigger/AudioEventTriggerSystem.js +15 -1
  251. package/src/engine/sound/simulation/core/AcousticMedium.js +2 -2
  252. package/src/engine/sound/simulation/definition/AcousticDirectivity.js +2 -2
  253. package/src/engine/sound/simulation/definition/AcousticMaterial.d.ts.map +1 -1
  254. package/src/engine/sound/simulation/definition/AcousticMaterial.js +11 -7
  255. package/src/engine/sound/sopra/README.md +768 -644
  256. package/src/engine/sound/sopra/SopraEngine.d.ts +104 -8
  257. package/src/engine/sound/sopra/SopraEngine.d.ts.map +1 -1
  258. package/src/engine/sound/sopra/SopraEngine.js +327 -12
  259. package/src/engine/sound/sopra/definition/BusDefinition.d.ts.map +1 -1
  260. package/src/engine/sound/sopra/definition/BusDefinition.js +5 -4
  261. package/src/engine/sound/sopra/definition/DuckingRule.d.ts.map +1 -1
  262. package/src/engine/sound/sopra/definition/DuckingRule.js +7 -5
  263. package/src/engine/sound/sopra/definition/EventDescription.d.ts +28 -2
  264. package/src/engine/sound/sopra/definition/EventDescription.d.ts.map +1 -1
  265. package/src/engine/sound/sopra/definition/EventDescription.js +77 -17
  266. package/src/engine/sound/sopra/definition/EventDescriptionSerializationAdapter.d.ts +10 -0
  267. package/src/engine/sound/sopra/definition/EventDescriptionSerializationAdapter.d.ts.map +1 -1
  268. package/src/engine/sound/sopra/definition/EventDescriptionSerializationAdapter.js +77 -55
  269. package/src/engine/sound/sopra/definition/EventDescriptionSerializationUpgrader_0_1.d.ts +31 -0
  270. package/src/engine/sound/sopra/definition/EventDescriptionSerializationUpgrader_0_1.d.ts.map +1 -0
  271. package/src/engine/sound/sopra/definition/EventDescriptionSerializationUpgrader_0_1.js +75 -0
  272. package/src/engine/sound/sopra/definition/MixerSnapshot.js +2 -2
  273. package/src/engine/sound/sopra/definition/ParameterDefinition.d.ts.map +1 -1
  274. package/src/engine/sound/sopra/definition/ParameterDefinition.js +7 -5
  275. package/src/engine/sound/sopra/definition/clip/AbstractAudioClip.js +2 -2
  276. package/src/engine/sound/sopra/definition/clip/BlendContainerAudioClip.d.ts.map +1 -1
  277. package/src/engine/sound/sopra/definition/clip/BlendContainerAudioClip.js +4 -3
  278. package/src/engine/sound/sopra/definition/clip/ContainerAudioClip.js +2 -2
  279. package/src/engine/sound/sopra/definition/clip/RandomContainerAudioClip.js +3 -3
  280. package/src/engine/sound/sopra/definition/clip/SampleAudioClip.d.ts.map +1 -1
  281. package/src/engine/sound/sopra/definition/clip/SampleAudioClip.js +16 -9
  282. package/src/engine/sound/sopra/definition/clip/SilenceAudioClip.js +2 -2
  283. package/src/engine/sound/sopra/definition/clip/SwitchContainerAudioClip.d.ts +1 -1
  284. package/src/engine/sound/sopra/definition/clip/SwitchContainerAudioClip.d.ts.map +1 -1
  285. package/src/engine/sound/sopra/definition/clip/SwitchContainerAudioClip.js +2 -2
  286. package/src/engine/sound/sopra/definition/effect/AbstractAudioEffect.d.ts +38 -9
  287. package/src/engine/sound/sopra/definition/effect/AbstractAudioEffect.d.ts.map +1 -1
  288. package/src/engine/sound/sopra/definition/effect/AbstractAudioEffect.js +34 -5
  289. package/src/engine/sound/sopra/definition/effect/CompressorEffect.d.ts +7 -2
  290. package/src/engine/sound/sopra/definition/effect/CompressorEffect.d.ts.map +1 -1
  291. package/src/engine/sound/sopra/definition/effect/CompressorEffect.js +137 -120
  292. package/src/engine/sound/sopra/definition/effect/EqEffect.d.ts +3 -1
  293. package/src/engine/sound/sopra/definition/effect/EqEffect.d.ts.map +1 -1
  294. package/src/engine/sound/sopra/definition/effect/EqEffect.js +146 -128
  295. package/src/engine/sound/sopra/definition/effect/ReverbEffect.d.ts +1 -0
  296. package/src/engine/sound/sopra/definition/effect/ReverbEffect.d.ts.map +1 -1
  297. package/src/engine/sound/sopra/definition/effect/ReverbEffect.js +8 -3
  298. package/src/engine/sound/sopra/legacy/SoundEmitter.d.ts.map +1 -1
  299. package/src/engine/sound/sopra/legacy/SoundEmitter.js +357 -352
  300. package/src/engine/sound/sopra/legacy/SoundTrack.d.ts.map +1 -1
  301. package/src/engine/sound/sopra/legacy/SoundTrack.js +281 -278
  302. package/src/engine/sound/sopra/runtime/BusGraph.d.ts +44 -2
  303. package/src/engine/sound/sopra/runtime/BusGraph.d.ts.map +1 -1
  304. package/src/engine/sound/sopra/runtime/BusGraph.js +83 -43
  305. package/src/engine/sound/sopra/runtime/EffectChain.d.ts +96 -0
  306. package/src/engine/sound/sopra/runtime/EffectChain.d.ts.map +1 -0
  307. package/src/engine/sound/sopra/runtime/EffectChain.js +286 -0
  308. package/src/engine/sound/sopra/runtime/EffectParamOverrides.d.ts +123 -0
  309. package/src/engine/sound/sopra/runtime/EffectParamOverrides.d.ts.map +1 -0
  310. package/src/engine/sound/sopra/runtime/EffectParamOverrides.js +320 -0
  311. package/src/engine/sound/sopra/runtime/EventInstance.d.ts +55 -5
  312. package/src/engine/sound/sopra/runtime/EventInstance.d.ts.map +1 -1
  313. package/src/engine/sound/sopra/runtime/EventInstance.js +201 -26
  314. package/src/engine/sound/sopra/serialization/populateSopraSerializationRegistry.d.ts +2 -1
  315. package/src/engine/sound/sopra/serialization/populateSopraSerializationRegistry.d.ts.map +1 -1
  316. package/src/engine/sound/sopra/serialization/populateSopraSerializationRegistry.js +6 -1
  317. package/src/engine/sound/sopra/serialization/sopraSerializationHarness.d.ts +15 -0
  318. package/src/engine/sound/sopra/serialization/sopraSerializationHarness.d.ts.map +1 -1
  319. package/src/engine/sound/sopra/serialization/sopraSerializationHarness.js +32 -0
  320. package/src/engine/sound/sopra/util/MockAudioContext.d.ts.map +1 -1
  321. package/src/engine/sound/sopra/util/MockAudioContext.js +3 -0
  322. package/src/engine/sound/sopra/util/fadeOutAndStop.d.ts +13 -3
  323. package/src/engine/sound/sopra/util/fadeOutAndStop.d.ts.map +1 -1
  324. package/src/engine/sound/sopra/util/fadeOutAndStop.js +25 -13
  325. package/src/format/image/png/PNGReader.js +644 -644
  326. package/src/format/image/png/crc32.d.ts +1 -1
  327. package/src/format/image/png/crc32.js +7 -8
  328. package/src/shade/RENDERER_CONTRACT.md +6 -3
  329. package/src/shade/descriptor/binding/BindGroupLayoutDescriptor.js +2 -2
  330. package/src/shade/descriptor/binding/BindGroupLayoutEntry.d.ts.map +1 -1
  331. package/src/shade/descriptor/binding/BindGroupLayoutEntry.js +12 -8
  332. package/src/shade/descriptor/binding/StorageTextureBindingLayout.js +2 -2
  333. package/src/shade/descriptor/binding/TextureBindingLayout.js +2 -2
  334. package/src/shade/descriptor/blend/BlendComponent.js +2 -2
  335. package/src/shade/descriptor/pipeline/PipelineDescriptorBase.js +2 -2
  336. package/src/shade/descriptor/pipeline/PipelineLayoutDescriptor.js +2 -2
  337. package/src/shade/descriptor/pipeline/ProgrammableStage.js +2 -2
  338. package/src/shade/descriptor/pipeline/compute/ComputePipelineDescriptor.js +2 -2
  339. package/src/shade/descriptor/pipeline/render/ColorTargetState.js +2 -2
  340. package/src/shade/descriptor/pipeline/render/FragmentState.js +2 -2
  341. package/src/shade/descriptor/pipeline/render/PrimitiveState.js +2 -2
  342. package/src/shade/descriptor/pipeline/render/RenderPipelineDescriptor.d.ts.map +1 -1
  343. package/src/shade/descriptor/pipeline/render/RenderPipelineDescriptor.js +8 -5
  344. package/src/shade/descriptor/pipeline/render/VertexAttribute.js +2 -2
  345. package/src/shade/descriptor/texture/SamplerDescriptor.d.ts.map +1 -1
  346. package/src/shade/descriptor/texture/SamplerDescriptor.js +20 -12
  347. package/src/shade/descriptor/texture/TextureDescriptor.d.ts.map +1 -1
  348. package/src/shade/descriptor/texture/TextureDescriptor.js +11 -7
  349. package/src/shade/device/SHADE_DEVICE_FLOOR.d.ts +24 -0
  350. package/src/shade/device/SHADE_DEVICE_FLOOR.d.ts.map +1 -0
  351. package/src/shade/device/SHADE_DEVICE_FLOOR.js +34 -0
  352. package/src/shade/device/ShadeDeviceFailure.d.ts +12 -5
  353. package/src/shade/device/ShadeDeviceFailure.d.ts.map +1 -1
  354. package/src/shade/device/ShadeDeviceFailure.js +17 -8
  355. package/src/shade/device/ShadeDeviceFailureReason.d.ts +1 -1
  356. package/src/shade/device/ShadeDeviceFailureReason.js +2 -2
  357. package/src/shade/device/graph/BufferResourceDescriptor.d.ts.map +1 -1
  358. package/src/shade/device/graph/BufferResourceDescriptor.js +196 -193
  359. package/src/shade/device/graph/TextureResourceDescriptor.d.ts.map +1 -1
  360. package/src/shade/device/graph/TextureResourceDescriptor.js +178 -173
  361. package/src/shade/device/shade_device_floor_unmet.d.ts +13 -0
  362. package/src/shade/device/shade_device_floor_unmet.d.ts.map +1 -0
  363. package/src/shade/device/shade_device_floor_unmet.js +32 -0
  364. package/src/shade/device/timing/profile/sgpt_read_header.js +1 -1
  365. package/src/shade/device/timing/profile/sgpt_read_records.js +1 -1
  366. package/src/shade/device/timing/profile/sgpt_write_header.js +1 -1
  367. package/src/shade/device/timing/profile/sgpt_write_record.js +1 -1
  368. package/src/shade/renderer/Renderer.d.ts +2 -0
  369. package/src/shade/renderer/Renderer.d.ts.map +1 -1
  370. package/src/shade/renderer/Renderer.js +29 -55
  371. package/src/shade/renderer/binding/BufferBinding.js +2 -2
  372. package/src/shade/renderer/buffer/GPUBufferAllocator.d.ts.map +1 -1
  373. package/src/shade/renderer/buffer/GPUBufferAllocator.js +9 -0
  374. package/src/shade/renderer/buffer/buffer_pool_ops.d.ts +21 -12
  375. package/src/shade/renderer/buffer/buffer_pool_ops.d.ts.map +1 -1
  376. package/src/shade/renderer/buffer/buffer_pool_ops.js +18 -19
  377. package/src/shade/renderer/camera/Camera.js +2 -2
  378. package/src/shade/renderer/geometry/Attribute.js +2 -2
  379. package/src/shade/renderer/geometry/Geometry.js +2 -2
  380. package/src/shade/renderer/geometry/geometry_deduplicate_vertices.js +2 -2
  381. package/src/shade/renderer/geometry/meshlet/MeshletBatch.js +2 -2
  382. package/src/shade/renderer/geometry/virtual/format/checksum/vgeo_compute_asset_id.js +13 -13
  383. package/src/shade/renderer/geometry/virtual/format/checksum/vgeo_compute_directory_block_checksum.js +41 -41
  384. package/src/shade/renderer/geometry/virtual/format/checksum/vgeo_compute_frame_checksum.js +41 -41
  385. package/src/shade/renderer/geometry/virtual/format/checksum/vgeo_compute_header_checksum.js +25 -25
  386. package/src/shade/renderer/gpu_primitive/test/gpu_test.d.ts.map +1 -1
  387. package/src/shade/renderer/gpu_primitive/test/gpu_test.js +8 -11
  388. package/src/shade/renderer/loader/gltf/tiny-gltf.d.ts +1 -1
  389. package/src/shade/renderer/material/StandardShadeMaterial.d.ts.map +1 -1
  390. package/src/shade/renderer/material/StandardShadeMaterial.js +13 -8
  391. package/src/shade/renderer/pool/TransientResourcePool.d.ts +24 -0
  392. package/src/shade/renderer/pool/TransientResourcePool.d.ts.map +1 -1
  393. package/src/shade/renderer/pool/TransientResourcePool.js +41 -10
  394. package/src/shade/renderer/scene/optimization/geometry/internal/triangle_fingerprint_stream.d.ts.map +1 -1
  395. package/src/shade/renderer/scene/optimization/geometry/internal/triangle_fingerprint_stream.js +14 -5
  396. package/src/shade/renderer/scene/optimization/sampler2d_from_image_bitmap.js +1 -1
  397. package/src/shade/renderer/shader/ComputeShader.d.ts.map +1 -1
  398. package/src/shade/renderer/shader/ComputeShader.js +18 -2
  399. package/src/shade/renderer/shader/ImageShader.d.ts.map +1 -1
  400. package/src/shade/renderer/shader/ImageShader.js +230 -218
  401. package/src/shade/renderer/shader/type/WGSLStructField.js +2 -2
  402. package/src/shade/renderer/shader/type/WebGPUArray.js +2 -2
  403. package/src/shade/renderer/shader/type/WebGPUStruct.d.ts.map +1 -1
  404. package/src/shade/renderer/shader/type/WebGPUStruct.js +9 -6
  405. package/src/shade/renderer/texture/ShadeTexture.d.ts.map +1 -1
  406. package/src/shade/renderer/texture/ShadeTexture.js +17 -10
  407. package/src/shade/renderer/texture/mipmaps/WebGPUMipmapGenerator.js +2 -2
  408. package/src/shade/renderer/water/surface/chunk_water_surface_sample.d.ts +4 -4
  409. package/src/shade/renderer/water/surface/chunk_water_surface_sample.js +6 -6
  410. package/src/shade/renderer/water/surface/particles/GPUWaterParticles.d.ts.map +1 -1
  411. package/src/shade/renderer/water/surface/particles/GPUWaterParticles.js +46 -55
  412. package/src/shade/renderer/water/surface/particles/WATER_PARTICLE_STRUCT.d.ts +3 -3
  413. package/src/shade/renderer/water/surface/particles/WATER_PARTICLE_STRUCT.d.ts.map +1 -1
  414. package/src/shade/renderer/water/surface/particles/WATER_PARTICLE_STRUCT.js +14 -4
  415. package/src/shade/renderer/water/surface/particles/chunk_water_particle.d.ts +10 -1
  416. package/src/shade/renderer/water/surface/particles/chunk_water_particle.d.ts.map +1 -1
  417. package/src/shade/renderer/water/surface/particles/chunk_water_particle.js +82 -40
  418. package/src/shade/renderer/water/surface/particles/chunk_water_particle_step.d.ts +4 -1
  419. package/src/shade/renderer/water/surface/particles/chunk_water_particle_step.d.ts.map +1 -1
  420. package/src/shade/renderer/water/surface/particles/chunk_water_particle_step.js +8 -4
  421. package/src/shade/renderer/water/surface/particles/shader_water_particles.d.ts +98 -86
  422. package/src/shade/renderer/water/surface/particles/shader_water_particles.d.ts.map +1 -1
  423. package/src/shade/renderer/water/surface/particles/shader_water_particles.js +440 -298
  424. package/src/view/common/HTMLElementCacheKey.d.ts.map +1 -1
  425. package/src/view/common/HTMLElementCacheKey.js +4 -3
  426. package/src/view/graphics/GraphicsContextFailureView.d.ts +1 -2
  427. package/src/view/graphics/GraphicsContextFailureView.d.ts.map +1 -1
  428. package/src/view/graphics/GraphicsContextFailureView.js +1 -2
  429. package/src/view/minimap/MinimapMarker.js +2 -2
  430. package/src/engine/network/transport/Channel.js +0 -336
  431. package/src/engine/network/transport/ReliableCommandPipeline.js +0 -335
  432. package/src/engine/network/transport/fragments/FragmentAssembler.js +0 -350
  433. package/src/engine/network/transport/fragments/FragmentRetention.js +0 -191
  434. package/src/engine/network/transport/fragments/fragment_send.js +0 -157
  435. package/src/engine/network/transport/fragments/packet_size.js +0 -107
@@ -45,11 +45,12 @@ export class SopraEngine {
45
45
  */
46
46
  voiceManager: VoiceManager;
47
47
  /**
48
- * Listener world position for spatialization/attenuation. Null = no listener set yet (events play
49
- * unattenuated). In P3 this is driven from the ECS SoundListener.
50
- * @type {Vector3|null}
48
+ * Listener world position for spatialization/attenuation, read by index. Null = no listener set yet
49
+ * (events play unattenuated). Set it with {@link setListener}, which is also how a move is reported;
50
+ * the ECS `AudioEmitterSystem` drives it from the `SoundListener` entity's transform.
51
+ * @type {ArrayLike<number>|null}
51
52
  */
52
- listenerPosition: Vector3 | null;
53
+ listenerPosition: ArrayLike<number> | null;
53
54
  /**
54
55
  * @type {BaseAudioContext}
55
56
  */
@@ -88,9 +89,22 @@ export class SopraEngine {
88
89
  * feeding the old graph, so anything already playing is silenced by the swap rather than
89
90
  * re-routed. Swap between scenes, or stop what is playing first.
90
91
  *
92
+ * Every bus is built at its DEFINED gain, so by default a fader moved since — a player's volume
93
+ * setting, a bound parameter, a snapshot — is reset by the swap. That is right when the new tree IS
94
+ * the new mix (loading a scene's authored mix). When the tree changes but the mix should not —
95
+ * adding a bus to the tree the player has been adjusting — pass `keepVolumes`: each bus present in
96
+ * both trees keeps its fader where it was, moved the way {@link setBusVolume} moves it (an engaged
97
+ * duck on it carries over too), and buses new to the tree start at their defined gain. Only the
98
+ * faders carry: insert-effect parameters start from the new definitions, which may describe
99
+ * different effects — except one a {@link bindParameterToBusEffectParam} binding holds, which the new
100
+ * tree is built at the bound value of, with `keepVolumes` or without.
101
+ *
91
102
  * @param {BusDefinition[]} busDefinitions
103
+ * @param {{keepVolumes?: boolean}} [options]
92
104
  */
93
- setBuses(busDefinitions: BusDefinition[]): void;
105
+ setBuses(busDefinitions: BusDefinition[], { keepVolumes }?: {
106
+ keepVolumes?: boolean;
107
+ }): void;
94
108
  /**
95
109
  * Create (but do not start) an instance of an event.
96
110
  * @param {EventDescription} description
@@ -159,10 +173,18 @@ export class SopraEngine {
159
173
  */
160
174
  getParameter(name: string): number | undefined;
161
175
  /**
162
- * Set the listener world position used for 3D attenuation/culling.
163
- * @param {Vector3} position
176
+ * Set the listener world position used for 3D attenuation/culling, and report that it moved: every 3D
177
+ * instance re-attenuates against it on the next {@link update}, and none does again until the next
178
+ * call. Held by reference, so after writing into the same array, call this again with it.
179
+ * @param {ArrayLike<number>|null} position read by index
180
+ */
181
+ setListener(position: ArrayLike<number> | null): void;
182
+ /**
183
+ * Advanced by each {@link setListener}: what a 3D instance compares to tell whether the listener has
184
+ * moved since it last attenuated.
185
+ * @returns {number}
164
186
  */
165
- setListener(position: Vector3): void;
187
+ get listenerVersion(): number;
166
188
  /**
167
189
  * Register a parameter with a default value.
168
190
  * @param {string} name
@@ -182,6 +204,42 @@ export class SopraEngine {
182
204
  * @param {AnimationCurve} curve maps parameter value -> linear bus gain
183
205
  */
184
206
  bindParameterToBusVolume(name: string, busId: string, curve: AnimationCurve): void;
207
+ /**
208
+ * Drive a parameter of one of a bus's insert effects from a sopra parameter through an
209
+ * {@link AnimationCurve} — the effect's counterpart of {@link bindParameterToBusVolume}. A game sets
210
+ * one value (`health`); how far the world's lowpass closes for it is authored in the curve, not
211
+ * worked out in game code.
212
+ *
213
+ * Addressed as {@link setBusEffectParam}, and checked against the tree as it stands: a bus, effect or
214
+ * parameter it does not have throws here, where the binding was written. The parameter's value takes
215
+ * hold at once, without a glide: now if it has one, else when it first gets one.
216
+ *
217
+ * From then on the binding is a standing rule:
218
+ * - each change of the parameter moves the effect — now, or with a `timeConstant` above 0 as a glide
219
+ * ({@link approachBusEffectParam}), so a value set every frame is tracked smoothly;
220
+ * - every tree {@link setBuses} builds that has the target starts at the bound value, not at the
221
+ * definition it was rebuilt from;
222
+ * - over a tree without the target it does nothing, and holds again over the next tree that has it.
223
+ * (A binding cannot be removed, so it has to outlive a tree swap; a mistyped address is caught at
224
+ * the bind.)
225
+ *
226
+ * One binding per parameter and target: binding the same pair again replaces its curve and time
227
+ * constant, and moves the effect to the new curve as a change would — it adds nothing, so binding again
228
+ * after a {@link setBuses} that keeps the target is harmless. Two parameters bound to one target
229
+ * take turns — the last to change wins, and after a rebuild the later binding (a re-bind keeps its
230
+ * place). A direct {@link setBusEffectParam} on a bound effect holds until the parameter next changes.
231
+ *
232
+ * The address is positional, like every effect address: reorder a bus's `effects` and the binding
233
+ * follows whatever now sits at its index.
234
+ *
235
+ * @param {string} name sopra parameter, as {@link setParameter} sets it
236
+ * @param {string} busId
237
+ * @param {number} effectIndex position in the bus definition's `effects`
238
+ * @param {string} paramName one of that effect class's `parameters` (`'frequency'` on an `EqEffect`)
239
+ * @param {AnimationCurve} curve maps the parameter's value to the effect parameter's, in its own units
240
+ * @param {number} [timeConstant=0] seconds: 0 moves the effect now on each change; above 0 glides
241
+ */
242
+ bindParameterToBusEffectParam(name: string, busId: string, effectIndex: number, paramName: string, curve: AnimationCurve, timeConstant?: number): void;
185
243
  /**
186
244
  * @param {string} busId
187
245
  * @returns {number} linear gain
@@ -192,6 +250,44 @@ export class SopraEngine {
192
250
  * @param {number} linear linear gain
193
251
  */
194
252
  setBusVolume(busId: string, linear: number): void;
253
+ /**
254
+ * Move a parameter of one of a bus's insert effects ({@link BusDefinition.effects}), now.
255
+ *
256
+ * The effect is addressed by its position in the bus definition's `effects`, the parameter by one of
257
+ * its class's `parameters` — the name of the definition field it starts from (`'frequency'` on an
258
+ * `EqEffect`). It moves the bus's built copy only; the definition is never touched, and
259
+ * {@link setBuses} rebuilds from it. Whatever automation was in flight on the parameter is cancelled.
260
+ *
261
+ * @param {string} busId
262
+ * @param {number} effectIndex
263
+ * @param {string} name
264
+ * @param {number} value in the parameter's own units (Hz, dB, seconds, ...)
265
+ */
266
+ setBusEffectParam(busId: string, effectIndex: number, name: string, value: number): void;
267
+ /**
268
+ * Glide a parameter of one of a bus's insert effects toward `value` — a lowpass closing over the
269
+ * world as health runs out, a compressor's threshold riding a game state. Exponential, covering ~63%
270
+ * of the way per `timeConstant`, like the fader's ducking glide. Whatever was in flight is cancelled
271
+ * and held first, so a value sent every frame retargets from wherever the last glide had got to.
272
+ *
273
+ * Addressed as {@link setBusEffectParam}.
274
+ *
275
+ * @param {string} busId
276
+ * @param {number} effectIndex
277
+ * @param {string} name
278
+ * @param {number} value
279
+ * @param {number} timeConstant seconds, above 0
280
+ */
281
+ approachBusEffectParam(busId: string, effectIndex: number, name: string, value: number, timeConstant: number): void;
282
+ /**
283
+ * Where a bus effect's parameter was last sent (the target of a glide still in flight), or its
284
+ * defined value if it has not been moved.
285
+ * @param {string} busId
286
+ * @param {number} effectIndex
287
+ * @param {string} name
288
+ * @returns {number}
289
+ */
290
+ getBusEffectParam(busId: string, effectIndex: number, name: string): number;
195
291
  /**
196
292
  * Apply a {@link MixerSnapshot}: move each listed bus to its target gain. `duration` 0 snaps
197
293
  * instantly; > 0 click-safely ramps (a mix-state blend).
@@ -1 +1 @@
1
- {"version":3,"file":"SopraEngine.d.ts","sourceRoot":"","sources":["../../../../../src/engine/sound/sopra/SopraEngine.js"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"SopraEngine.d.ts","sourceRoot":"","sources":["../../../../../src/engine/sound/sopra/SopraEngine.js"],"names":[],"mappings":"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"}
@@ -62,23 +62,54 @@ export class SopraEngine {
62
62
  voiceManager = new VoiceManager();
63
63
 
64
64
  /**
65
- * Listener world position for spatialization/attenuation. Null = no listener set yet (events play
66
- * unattenuated). In P3 this is driven from the ECS SoundListener.
67
- * @type {Vector3|null}
65
+ * Listener world position for spatialization/attenuation, read by index. Null = no listener set yet
66
+ * (events play unattenuated). Set it with {@link setListener}, which is also how a move is reported;
67
+ * the ECS `AudioEmitterSystem` drives it from the `SoundListener` entity's transform.
68
+ * @type {ArrayLike<number>|null}
68
69
  */
69
70
  listenerPosition = null;
70
71
 
72
+ /**
73
+ * Advanced by every {@link setListener}. An instance re-attenuates when this differs from the value it
74
+ * last attenuated against, so between listener moves nothing is recomputed.
75
+ * @type {number}
76
+ */
77
+ #listenerVersion = 0;
78
+
71
79
  /**
72
80
  * @type {Set<EventInstance>}
73
81
  */
74
82
  #activeInstances = new Set();
75
83
 
84
+ /**
85
+ * Where {@link update} takes its snapshot of {@link #activeInstances}, kept rather than built each
86
+ * frame. Emptied after each update so it holds no instance past it.
87
+ * @type {EventInstance[]}
88
+ */
89
+ #updateSnapshot = [];
90
+
91
+ /**
92
+ * Whether an {@link update} is under way. An update reached from inside one — an instance's end
93
+ * handler ticking the engine — takes a snapshot of its own rather than overwrite the outer one.
94
+ * @type {boolean}
95
+ */
96
+ #updating = false;
97
+
76
98
  /**
77
99
  * Active ducking rules + their runtime state.
78
100
  * @type {{rule: DuckingRule, engaged: boolean, nominalDb: number}[]}
79
101
  */
80
102
  #duckers = [];
81
103
 
104
+ /**
105
+ * The standing rules of {@link bindParameterToBusEffectParam}, kept so {@link setBuses} can put each
106
+ * one back over the tree it builds.
107
+ * `held`: the binding has put its target at a bound value at least once — until then a value takes
108
+ * hold at once, after that a change glides (with a `timeConstant`).
109
+ * @type {{name: string, busId: string, effectIndex: number, paramName: string, curve: AnimationCurve, timeConstant: number, held: boolean}[]}
110
+ */
111
+ #effectBindings = [];
112
+
82
113
  /**
83
114
  * @param {BaseAudioContext} audioContext
84
115
  * @param {AudioNode} destinationNode master destination the bus root routes into
@@ -152,13 +183,48 @@ export class SopraEngine {
152
183
  * feeding the old graph, so anything already playing is silenced by the swap rather than
153
184
  * re-routed. Swap between scenes, or stop what is playing first.
154
185
  *
186
+ * Every bus is built at its DEFINED gain, so by default a fader moved since — a player's volume
187
+ * setting, a bound parameter, a snapshot — is reset by the swap. That is right when the new tree IS
188
+ * the new mix (loading a scene's authored mix). When the tree changes but the mix should not —
189
+ * adding a bus to the tree the player has been adjusting — pass `keepVolumes`: each bus present in
190
+ * both trees keeps its fader where it was, moved the way {@link setBusVolume} moves it (an engaged
191
+ * duck on it carries over too), and buses new to the tree start at their defined gain. Only the
192
+ * faders carry: insert-effect parameters start from the new definitions, which may describe
193
+ * different effects — except one a {@link bindParameterToBusEffectParam} binding holds, which the new
194
+ * tree is built at the bound value of, with `keepVolumes` or without.
195
+ *
155
196
  * @param {BusDefinition[]} busDefinitions
197
+ * @param {{keepVolumes?: boolean}} [options]
156
198
  */
157
- setBuses(busDefinitions) {
158
- this.busGraph.dispose();
199
+ setBuses(busDefinitions, { keepVolumes = false } = {}) {
200
+ const previous = this.busGraph;
201
+
202
+ /**
203
+ * fader positions to carry over: id -> linear gain
204
+ * @type {Map<string, number>}
205
+ */
206
+ const kept = new Map();
207
+
208
+ if (keepVolumes) {
209
+ for (const [id, bus] of previous.buses) {
210
+ kept.set(id, bus.nominal);
211
+ }
212
+ }
213
+
214
+ previous.dispose();
159
215
 
160
216
  this.busGraph = new BusGraph(this.audioContext, this.destination);
161
217
  this.busGraph.build(busDefinitions);
218
+
219
+ for (const [id, linear] of kept) {
220
+ if (this.busGraph.has(id)) {
221
+ this.setBusVolume(id, linear);
222
+ }
223
+ }
224
+
225
+ // a binding is a standing rule, not a move made once: the rebuilt effect is put at the bound value
226
+ // at once, where it would otherwise sit at its definition until the parameter next changed
227
+ this.#reassertEffectBindings(null);
162
228
  }
163
229
 
164
230
  /**
@@ -265,11 +331,23 @@ export class SopraEngine {
265
331
  }
266
332
 
267
333
  /**
268
- * Set the listener world position used for 3D attenuation/culling.
269
- * @param {Vector3} position
334
+ * Set the listener world position used for 3D attenuation/culling, and report that it moved: every 3D
335
+ * instance re-attenuates against it on the next {@link update}, and none does again until the next
336
+ * call. Held by reference, so after writing into the same array, call this again with it.
337
+ * @param {ArrayLike<number>|null} position read by index
270
338
  */
271
339
  setListener(position) {
272
340
  this.listenerPosition = position;
341
+ this.#listenerVersion++;
342
+ }
343
+
344
+ /**
345
+ * Advanced by each {@link setListener}: what a 3D instance compares to tell whether the listener has
346
+ * moved since it last attenuated.
347
+ * @returns {number}
348
+ */
349
+ get listenerVersion() {
350
+ return this.#listenerVersion;
273
351
  }
274
352
 
275
353
  /**
@@ -278,7 +356,15 @@ export class SopraEngine {
278
356
  * @param {number} [defaultValue]
279
357
  */
280
358
  defineParameter(name, defaultValue = 0) {
359
+ const fresh = !this.parameters.has(name);
360
+
281
361
  this.parameters.define(name, defaultValue);
362
+
363
+ // `define` runs no binding, and a later `set` to the same value is no change, so an effect bound
364
+ // before its parameter existed would otherwise wait for a different value - or the next setBuses
365
+ if (fresh) {
366
+ this.#reassertEffectBindings(name);
367
+ }
282
368
  }
283
369
 
284
370
  /**
@@ -300,6 +386,169 @@ export class SopraEngine {
300
386
  this.parameters.bind(name, (value) => this.setBusVolume(busId, curve.evaluate(value)));
301
387
  }
302
388
 
389
+ /**
390
+ * Drive a parameter of one of a bus's insert effects from a sopra parameter through an
391
+ * {@link AnimationCurve} — the effect's counterpart of {@link bindParameterToBusVolume}. A game sets
392
+ * one value (`health`); how far the world's lowpass closes for it is authored in the curve, not
393
+ * worked out in game code.
394
+ *
395
+ * Addressed as {@link setBusEffectParam}, and checked against the tree as it stands: a bus, effect or
396
+ * parameter it does not have throws here, where the binding was written. The parameter's value takes
397
+ * hold at once, without a glide: now if it has one, else when it first gets one.
398
+ *
399
+ * From then on the binding is a standing rule:
400
+ * - each change of the parameter moves the effect — now, or with a `timeConstant` above 0 as a glide
401
+ * ({@link approachBusEffectParam}), so a value set every frame is tracked smoothly;
402
+ * - every tree {@link setBuses} builds that has the target starts at the bound value, not at the
403
+ * definition it was rebuilt from;
404
+ * - over a tree without the target it does nothing, and holds again over the next tree that has it.
405
+ * (A binding cannot be removed, so it has to outlive a tree swap; a mistyped address is caught at
406
+ * the bind.)
407
+ *
408
+ * One binding per parameter and target: binding the same pair again replaces its curve and time
409
+ * constant, and moves the effect to the new curve as a change would — it adds nothing, so binding again
410
+ * after a {@link setBuses} that keeps the target is harmless. Two parameters bound to one target
411
+ * take turns — the last to change wins, and after a rebuild the later binding (a re-bind keeps its
412
+ * place). A direct {@link setBusEffectParam} on a bound effect holds until the parameter next changes.
413
+ *
414
+ * The address is positional, like every effect address: reorder a bus's `effects` and the binding
415
+ * follows whatever now sits at its index.
416
+ *
417
+ * @param {string} name sopra parameter, as {@link setParameter} sets it
418
+ * @param {string} busId
419
+ * @param {number} effectIndex position in the bus definition's `effects`
420
+ * @param {string} paramName one of that effect class's `parameters` (`'frequency'` on an `EqEffect`)
421
+ * @param {AnimationCurve} curve maps the parameter's value to the effect parameter's, in its own units
422
+ * @param {number} [timeConstant=0] seconds: 0 moves the effect now on each change; above 0 glides
423
+ */
424
+ bindParameterToBusEffectParam(name, busId, effectIndex, paramName, curve, timeConstant = 0) {
425
+ assert.isString(name, 'name');
426
+ assert.defined(curve, 'curve');
427
+ assert.isFinite(timeConstant, 'timeConstant');
428
+ assert.greaterThanOrEqual(timeConstant, 0, 'timeConstant');
429
+
430
+ // throws naming what the tree lacks
431
+ this.busGraph.getEffectParam(busId, effectIndex, paramName);
432
+
433
+ const parameters = this.parameters;
434
+ const existing = this.#findEffectBinding(name, busId, effectIndex, paramName);
435
+ const binding = { name, busId, effectIndex, paramName, curve, timeConstant, held: existing !== null && existing.held };
436
+
437
+ // Put the effect at the bound value BEFORE registering or replacing anything, so a curve that cannot
438
+ // be applied leaves no half-made binding behind. A new binding takes hold as a move, not a glide - it
439
+ // does not sweep in from wherever the definition left the effect; one replacing a binding that
440
+ // already holds the effect moves it the way a change would.
441
+ if (parameters.has(name)) {
442
+ this.#applyEffectBinding(binding, parameters.get(name), binding.held ? timeConstant : 0);
443
+ }
444
+
445
+ if (existing !== null) {
446
+ // the store already calls the one callback this pair has, and it reads the record
447
+ existing.curve = curve;
448
+ existing.timeConstant = timeConstant;
449
+ existing.held = binding.held;
450
+
451
+ return;
452
+ }
453
+
454
+ this.#effectBindings.push(binding);
455
+
456
+ // the store calls a callback once as it is bound, when the parameter has a value; that one is
457
+ // already applied above
458
+ let bound = false;
459
+
460
+ parameters.bind(name, (value) => {
461
+ if (bound) {
462
+ // a parameter's first value takes hold; only a change after that is a glide
463
+ this.#applyEffectBinding(binding, value, binding.held ? binding.timeConstant : 0);
464
+ }
465
+ });
466
+
467
+ bound = true;
468
+ }
469
+
470
+ /**
471
+ * @param {string} name
472
+ * @param {string} busId
473
+ * @param {number} effectIndex
474
+ * @param {string} paramName
475
+ * @returns {{name: string, busId: string, effectIndex: number, paramName: string, curve: AnimationCurve, timeConstant: number, held: boolean}|null}
476
+ */
477
+ #findEffectBinding(name, busId, effectIndex, paramName) {
478
+ const bindings = this.#effectBindings;
479
+
480
+ for (let i = 0; i < bindings.length; i++) {
481
+ const b = bindings[i];
482
+
483
+ if (b.name === name && b.busId === busId && b.effectIndex === effectIndex && b.paramName === paramName) {
484
+ return b;
485
+ }
486
+ }
487
+
488
+ return null;
489
+ }
490
+
491
+ /**
492
+ * Put every effect binding — or only those of parameter `name` — at its bound value now, over the
493
+ * current tree. Each is tried: one whose curve cannot be applied (a stored value it cannot evaluate)
494
+ * does not keep the rest from holding, and the first such failure is thrown once they all have.
495
+ * @param {string|null} name null: every binding
496
+ */
497
+ #reassertEffectBindings(name) {
498
+ const bindings = this.#effectBindings;
499
+ const parameters = this.parameters;
500
+
501
+ let failure = null;
502
+
503
+ for (let i = 0; i < bindings.length; i++) {
504
+ const binding = bindings[i];
505
+
506
+ if ((name !== null && binding.name !== name) || !parameters.has(binding.name)) {
507
+ continue;
508
+ }
509
+
510
+ try {
511
+ this.#applyEffectBinding(binding, parameters.get(binding.name), 0);
512
+ } catch (e) {
513
+ if (failure === null) {
514
+ failure = e;
515
+ }
516
+ }
517
+ }
518
+
519
+ if (failure !== null) {
520
+ throw failure;
521
+ }
522
+ }
523
+
524
+ /**
525
+ * Put one effect binding's target at the curve's value for `value`, over the current tree — if it has
526
+ * that target at all (see {@link bindParameterToBusEffectParam}).
527
+ * @param {{busId: string, effectIndex: number, paramName: string, curve: AnimationCurve, held: boolean}} binding
528
+ * @param {number} value the sopra parameter's
529
+ * @param {number} timeConstant 0 moves it now; above 0 glides
530
+ */
531
+ #applyEffectBinding(binding, value, timeConstant) {
532
+ const graph = this.busGraph;
533
+ const busId = binding.busId;
534
+ const effectIndex = binding.effectIndex;
535
+ const paramName = binding.paramName;
536
+
537
+ if (!graph.hasEffectParam(busId, effectIndex, paramName)) {
538
+ return;
539
+ }
540
+
541
+ const target = binding.curve.evaluate(value);
542
+
543
+ if (timeConstant > 0) {
544
+ graph.approachEffectParam(busId, effectIndex, paramName, target, timeConstant);
545
+ } else {
546
+ graph.setEffectParam(busId, effectIndex, paramName, target);
547
+ }
548
+
549
+ binding.held = true;
550
+ }
551
+
303
552
  /**
304
553
  * @param {string} busId
305
554
  * @returns {number} linear gain
@@ -318,6 +567,53 @@ export class SopraEngine {
318
567
  this.#reduck(busId);
319
568
  }
320
569
 
570
+ /**
571
+ * Move a parameter of one of a bus's insert effects ({@link BusDefinition.effects}), now.
572
+ *
573
+ * The effect is addressed by its position in the bus definition's `effects`, the parameter by one of
574
+ * its class's `parameters` — the name of the definition field it starts from (`'frequency'` on an
575
+ * `EqEffect`). It moves the bus's built copy only; the definition is never touched, and
576
+ * {@link setBuses} rebuilds from it. Whatever automation was in flight on the parameter is cancelled.
577
+ *
578
+ * @param {string} busId
579
+ * @param {number} effectIndex
580
+ * @param {string} name
581
+ * @param {number} value in the parameter's own units (Hz, dB, seconds, ...)
582
+ */
583
+ setBusEffectParam(busId, effectIndex, name, value) {
584
+ this.busGraph.setEffectParam(busId, effectIndex, name, value);
585
+ }
586
+
587
+ /**
588
+ * Glide a parameter of one of a bus's insert effects toward `value` — a lowpass closing over the
589
+ * world as health runs out, a compressor's threshold riding a game state. Exponential, covering ~63%
590
+ * of the way per `timeConstant`, like the fader's ducking glide. Whatever was in flight is cancelled
591
+ * and held first, so a value sent every frame retargets from wherever the last glide had got to.
592
+ *
593
+ * Addressed as {@link setBusEffectParam}.
594
+ *
595
+ * @param {string} busId
596
+ * @param {number} effectIndex
597
+ * @param {string} name
598
+ * @param {number} value
599
+ * @param {number} timeConstant seconds, above 0
600
+ */
601
+ approachBusEffectParam(busId, effectIndex, name, value, timeConstant) {
602
+ this.busGraph.approachEffectParam(busId, effectIndex, name, value, timeConstant);
603
+ }
604
+
605
+ /**
606
+ * Where a bus effect's parameter was last sent (the target of a glide still in flight), or its
607
+ * defined value if it has not been moved.
608
+ * @param {string} busId
609
+ * @param {number} effectIndex
610
+ * @param {string} name
611
+ * @returns {number}
612
+ */
613
+ getBusEffectParam(busId, effectIndex, name) {
614
+ return this.busGraph.getEffectParam(busId, effectIndex, name);
615
+ }
616
+
321
617
  /**
322
618
  * Apply a {@link MixerSnapshot}: move each listed bus to its target gain. `duration` 0 snaps
323
619
  * instantly; > 0 click-safely ramps (a mix-state blend).
@@ -362,13 +658,32 @@ export class SopraEngine {
362
658
  * @param {number} [now] context time; defaults to the live clock
363
659
  */
364
660
  update(now = this.currentTime) {
365
- const listenerPosition = this.listenerPosition;
661
+ /*
662
+ Snapshot: an instance may finish (and remove itself) during its own update, and one played from
663
+ inside an update waits for the next. Written by index into a kept array up to a count, and
664
+ nulled after, rather than emptied with `length = 0`, which lets V8 trim the store it would only
665
+ grow back on the next frame.
666
+ */
667
+ const nested = this.#updating;
668
+ const instances = nested ? [] : this.#updateSnapshot;
669
+
670
+ let count = 0;
671
+
672
+ for (const instance of this.#activeInstances) {
673
+ instances[count++] = instance;
674
+ }
366
675
 
367
- // snapshot — an instance may finish (and remove itself) during its own update
368
- const instances = [...this.#activeInstances];
676
+ this.#updating = true;
677
+
678
+ try {
679
+ for (let i = 0; i < count; i++) {
680
+ // each reads the listener itself, with the version that goes with it
681
+ instances[i].update(now);
682
+ }
683
+ } finally {
684
+ this.#updating = nested;
369
685
 
370
- for (let i = 0; i < instances.length; i++) {
371
- instances[i].update(now, listenerPosition);
686
+ instances.fill(null, 0, count);
372
687
  }
373
688
 
374
689
  this.#updateDuckers();
@@ -1 +1 @@
1
- {"version":3,"file":"BusDefinition.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/sound/sopra/definition/BusDefinition.js"],"names":[],"mappings":"AAKA;;GAEG;AAEH;;;;GAIG;AACH;IAiCI;;;;;OAKG;IACH,gBAJW,MAAM,yCACN;QAAC,QAAQ,CAAC,EAAC,MAAM,CAAC;QAAC,MAAM,CAAC,EAAC,MAAM,CAAC;QAAC,OAAO,CAAC,EAAC,mBAAmB,EAAE,CAAC;QAAC,KAAK,CAAC,EAAC;YAAC,WAAW,EAAC,MAAM,CAAC;YAAA,OAAO,EAAC,MAAM,CAAA;SAAC,EAAE,CAAA;KAAC,GAC9G,aAAa,CAYzB;IA/CD;;;OAGG;IACH,IAFU,MAAM,CAER;IAER;;;;OAIG;IACH,UAFU,MAAM,CAEF;IAEd;;;OAGG;IACH,QAFU,MAAM,CAEL;IAEX;;;OAGG;IACH,SAFU,mBAAmB,EAAE,CAElB;IAEb;;;OAGG;IACH,OAFU;QAAC,WAAW,EAAC,MAAM,CAAC;QAAC,OAAO,EAAC,MAAM,CAAA;KAAC,EAAE,CAErC;IAoBX;;;;OAIG;IACH,cAHW,aAAa,GACX,OAAO,CA0BnB;IAED,eAgBC;IAED,uBAUC;IAED;;;;;;;;;;;;MAQC;IAED;;;;;;aAMC;CACJ;;;;kCAzIY,OAAO,iCAAiC,EAAE,mBAAmB"}
1
+ {"version":3,"file":"BusDefinition.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/sound/sopra/definition/BusDefinition.js"],"names":[],"mappings":"AAMA;;GAEG;AAEH;;;;GAIG;AACH;IAiCI;;;;;OAKG;IACH,gBAJW,MAAM,yCACN;QAAC,QAAQ,CAAC,EAAC,MAAM,CAAC;QAAC,MAAM,CAAC,EAAC,MAAM,CAAC;QAAC,OAAO,CAAC,EAAC,mBAAmB,EAAE,CAAC;QAAC,KAAK,CAAC,EAAC;YAAC,WAAW,EAAC,MAAM,CAAC;YAAA,OAAO,EAAC,MAAM,CAAA;SAAC,EAAE,CAAA;KAAC,GAC9G,aAAa,CAYzB;IA/CD;;;OAGG;IACH,IAFU,MAAM,CAER;IAER;;;;OAIG;IACH,UAFU,MAAM,CAEF;IAEd;;;OAGG;IACH,QAFU,MAAM,CAEL;IAEX;;;OAGG;IACH,SAFU,mBAAmB,EAAE,CAElB;IAEb;;;OAGG;IACH,OAFU;QAAC,WAAW,EAAC,MAAM,CAAC;QAAC,OAAO,EAAC,MAAM,CAAA;KAAC,EAAE,CAErC;IAoBX;;;;OAIG;IACH,cAHW,aAAa,GACX,OAAO,CA0BnB;IAED,eAgBC;IAED,uBAUC;IAED;;;;;;;;;;;;MAQC;IAED;;;;;;aAMC;CACJ;;;;kCAzIY,OAAO,iCAAiC,EAAE,mBAAmB"}
@@ -1,4 +1,5 @@
1
- import { combine_hash } from "../../../../core/collection/array/combine_hash.js";
1
+ import { hash_mix2 } from "../../../../core/math/hash/hash_mix2.js";
2
+ import { hash_mix3 } from "../../../../core/math/hash/hash_mix3.js";
2
3
  import { computeHashFloat } from "../../../../core/primitives/numbers/computeHashFloat.js";
3
4
  import { computeStringHash } from "../../../../core/primitives/strings/computeStringHash.js";
4
5
  import { deserializeAudioEffectFromJSON, serializeAudioEffectToJSON } from "../serialization/sopraJSON.js";
@@ -95,18 +96,18 @@ export class BusDefinition {
95
96
  }
96
97
 
97
98
  hash() {
98
- let h = combine_hash(
99
+ let h = hash_mix3(
99
100
  computeStringHash(this.id),
100
101
  computeStringHash(this.parentId),
101
102
  computeHashFloat(this.gainDb)
102
103
  );
103
104
 
104
105
  for (let i = 0; i < this.effects.length; i++) {
105
- h = combine_hash(h, this.effects[i].hash());
106
+ h = hash_mix2(h, this.effects[i].hash());
106
107
  }
107
108
 
108
109
  for (let i = 0; i < this.sends.length; i++) {
109
- h = combine_hash(h, computeStringHash(this.sends[i].targetBusId), computeHashFloat(this.sends[i].levelDb));
110
+ h = hash_mix3(h, computeStringHash(this.sends[i].targetBusId), computeHashFloat(this.sends[i].levelDb));
110
111
  }
111
112
 
112
113
  return h;
@@ -1 +1 @@
1
- {"version":3,"file":"DuckingRule.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/sound/sopra/definition/DuckingRule.js"],"names":[],"mappings":"AAIA;;;;;;;GAOG;AACH;IAgCI;;;OAGG;IACH,qEAHW;QAAC,YAAY,CAAC,EAAC,MAAM,CAAC;QAAC,WAAW,CAAC,EAAC,MAAM,CAAC;QAAC,MAAM,CAAC,EAAC,MAAM,CAAC;QAAC,MAAM,CAAC,EAAC,MAAM,CAAC;QAAC,OAAO,CAAC,EAAC,MAAM,CAAA;KAAC,GAC1F,WAAW,CAYvB;IA5CD;;;OAGG;IACH,cAFU,MAAM,CAEE;IAElB;;;OAGG;IACH,aAFU,MAAM,CAEC;IAEjB;;;OAGG;IACH,QAFU,MAAM,CAEH;IAEb;;;OAGG;IACH,QAFU,MAAM,CAEF;IAEd;;;OAGG;IACH,SAFU,MAAM,CAEF;IAkBd;;;OAGG;IACH,cAHW,WAAW,GACT,OAAO,CAQnB;IAED,eAQC;IAED,qBAEC;IAED;;;;;;MAQC;IAED;;;;;;aAMC;CACJ"}
1
+ {"version":3,"file":"DuckingRule.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/sound/sopra/definition/DuckingRule.js"],"names":[],"mappings":"AAIA;;;;;;;GAOG;AACH;IAgCI;;;OAGG;IACH,qEAHW;QAAC,YAAY,CAAC,EAAC,MAAM,CAAC;QAAC,WAAW,CAAC,EAAC,MAAM,CAAC;QAAC,MAAM,CAAC,EAAC,MAAM,CAAC;QAAC,MAAM,CAAC,EAAC,MAAM,CAAC;QAAC,OAAO,CAAC,EAAC,MAAM,CAAA;KAAC,GAC1F,WAAW,CAYvB;IA5CD;;;OAGG;IACH,cAFU,MAAM,CAEE;IAElB;;;OAGG;IACH,aAFU,MAAM,CAEC;IAEjB;;;OAGG;IACH,QAFU,MAAM,CAEH;IAEb;;;OAGG;IACH,QAFU,MAAM,CAEF;IAEd;;;OAGG;IACH,SAFU,MAAM,CAEF;IAkBd;;;OAGG;IACH,cAHW,WAAW,GACT,OAAO,CAQnB;IAED,eAUC;IAED,qBAEC;IAED;;;;;;MAQC;IAED;;;;;;aAMC;CACJ"}
@@ -1,4 +1,4 @@
1
- import { combine_hash } from "../../../../core/collection/array/combine_hash.js";
1
+ import { hash_mix3 } from "../../../../core/math/hash/hash_mix3.js";
2
2
  import { computeHashFloat } from "../../../../core/primitives/numbers/computeHashFloat.js";
3
3
  import { computeStringHash } from "../../../../core/primitives/strings/computeStringHash.js";
4
4
 
@@ -71,10 +71,12 @@ export class DuckingRule {
71
71
  }
72
72
 
73
73
  hash() {
74
- return combine_hash(
75
- computeStringHash(this.triggerBusId),
76
- computeStringHash(this.targetBusId),
77
- computeHashFloat(this.duckDb),
74
+ return hash_mix3(
75
+ hash_mix3(
76
+ computeStringHash(this.triggerBusId),
77
+ computeStringHash(this.targetBusId),
78
+ computeHashFloat(this.duckDb)
79
+ ),
78
80
  computeHashFloat(this.attack),
79
81
  computeHashFloat(this.release)
80
82
  );