@jgengine/core 0.9.0 → 0.11.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 (631) hide show
  1. package/CHANGELOG.md +34 -3
  2. package/LICENSE +203 -661
  3. package/README.md +1 -1
  4. package/dist/ai/crowd.d.ts +55 -0
  5. package/dist/ai/crowd.js +114 -0
  6. package/dist/ai/flock.d.ts +5 -2
  7. package/dist/ai/flock.js +5 -2
  8. package/dist/ai/groupAssist.d.ts +1 -0
  9. package/dist/ai/groupAssist.js +1 -0
  10. package/dist/ai/heatSystem.d.ts +76 -0
  11. package/dist/ai/heatSystem.js +97 -0
  12. package/dist/ai/interestScheduler.d.ts +107 -0
  13. package/dist/ai/interestScheduler.js +118 -0
  14. package/dist/ai/jobBoard.d.ts +1 -0
  15. package/dist/ai/jobBoard.js +1 -0
  16. package/dist/ai/laneSelect.d.ts +5 -2
  17. package/dist/ai/laneSelect.js +5 -2
  18. package/dist/ai/mobBrain.d.ts +1 -0
  19. package/dist/ai/mobBrain.js +1 -0
  20. package/dist/ai/spawnDirector.d.ts +19 -1
  21. package/dist/ai/spawnDirector.js +53 -26
  22. package/dist/ai/spawnPoint.d.ts +7 -0
  23. package/dist/ai/spawnPoint.js +7 -0
  24. package/dist/ai/targetAcquisition.d.ts +84 -0
  25. package/dist/ai/targetAcquisition.js +92 -0
  26. package/dist/anim/easing.d.ts +19 -0
  27. package/dist/anim/easing.js +19 -0
  28. package/dist/anim/oscillator.d.ts +12 -0
  29. package/dist/anim/oscillator.js +25 -0
  30. package/dist/area/areaEffectField.d.ts +127 -0
  31. package/dist/area/areaEffectField.js +175 -0
  32. package/dist/area/stackPolicy.d.ts +47 -0
  33. package/dist/area/stackPolicy.js +99 -0
  34. package/dist/audio/audioFalloff.d.ts +5 -2
  35. package/dist/audio/music.d.ts +53 -0
  36. package/dist/audio/music.js +34 -0
  37. package/dist/audio/synth.d.ts +60 -0
  38. package/dist/audio/synth.js +8 -0
  39. package/dist/authoring.d.ts +15 -0
  40. package/dist/authoring.js +15 -0
  41. package/dist/board/laneBoard.d.ts +13 -0
  42. package/dist/board/laneBoard.js +13 -0
  43. package/dist/board/timelineBoard.d.ts +10 -0
  44. package/dist/board/timelineBoard.js +10 -0
  45. package/dist/combat/abilityKit.d.ts +18 -0
  46. package/dist/combat/abilityKit.js +24 -9
  47. package/dist/combat/animationState.d.ts +5 -0
  48. package/dist/combat/animationState.js +5 -0
  49. package/dist/combat/breakMeters.d.ts +10 -0
  50. package/dist/combat/breakMeters.js +10 -0
  51. package/dist/combat/castRunner.d.ts +5 -0
  52. package/dist/combat/castRunner.js +5 -0
  53. package/dist/combat/comboPoints.d.ts +5 -0
  54. package/dist/combat/comboPoints.js +5 -0
  55. package/dist/combat/comboString.d.ts +5 -0
  56. package/dist/combat/comboString.js +5 -0
  57. package/dist/combat/damageInterceptors.d.ts +192 -0
  58. package/dist/combat/damageInterceptors.js +251 -0
  59. package/dist/combat/damageMatchup.d.ts +68 -0
  60. package/dist/combat/damageMatchup.js +42 -0
  61. package/dist/combat/damageResolution.d.ts +63 -0
  62. package/dist/combat/damageResolution.js +50 -0
  63. package/dist/combat/death.d.ts +7 -1
  64. package/dist/combat/death.js +5 -0
  65. package/dist/combat/deathReason.d.ts +14 -0
  66. package/dist/combat/deathReason.js +1 -0
  67. package/dist/combat/defensiveWindow.d.ts +5 -0
  68. package/dist/combat/defensiveWindow.js +5 -0
  69. package/dist/combat/dotField.d.ts +47 -0
  70. package/dist/combat/dotField.js +52 -0
  71. package/dist/combat/downed.d.ts +5 -0
  72. package/dist/combat/downed.js +5 -0
  73. package/dist/combat/effects.d.ts +5 -0
  74. package/dist/combat/effects.js +5 -0
  75. package/dist/combat/encounterSequence.d.ts +258 -0
  76. package/dist/combat/encounterSequence.js +426 -0
  77. package/dist/combat/hitReaction.d.ts +57 -1
  78. package/dist/combat/hitReaction.js +45 -5
  79. package/dist/combat/magazine.d.ts +54 -0
  80. package/dist/combat/magazine.js +96 -0
  81. package/dist/combat/projectiles.d.ts +7 -2
  82. package/dist/combat/projectiles.js +48 -17
  83. package/dist/combat/receivedDamage.d.ts +117 -0
  84. package/dist/combat/receivedDamage.js +92 -0
  85. package/dist/combat/regenShield.d.ts +39 -0
  86. package/dist/combat/regenShield.js +49 -0
  87. package/dist/combat/renderCues.d.ts +51 -0
  88. package/dist/combat/renderCues.js +44 -0
  89. package/dist/combat/resourcePool.d.ts +5 -0
  90. package/dist/combat/resourcePool.js +5 -0
  91. package/dist/combat/rewardAllocation.d.ts +121 -0
  92. package/dist/combat/rewardAllocation.js +251 -0
  93. package/dist/combat/shotOrigin.d.ts +30 -1
  94. package/dist/combat/shotOrigin.js +70 -2
  95. package/dist/combat/statusApplication.d.ts +96 -0
  96. package/dist/combat/statusApplication.js +81 -0
  97. package/dist/combat/telegraph.d.ts +11 -2
  98. package/dist/combat/telegraph.js +11 -2
  99. package/dist/combat/thresholdCrossings.d.ts +85 -0
  100. package/dist/combat/thresholdCrossings.js +116 -0
  101. package/dist/combat.d.ts +34 -0
  102. package/dist/combat.js +34 -0
  103. package/dist/commands/commandRegistry.d.ts +11 -0
  104. package/dist/commands/commandRegistry.js +9 -2
  105. package/dist/crafting/crop.d.ts +18 -0
  106. package/dist/crafting/crop.js +18 -0
  107. package/dist/crafting/production.d.ts +5 -0
  108. package/dist/crafting/production.js +5 -0
  109. package/dist/devtools/rewriteTunables.d.ts +17 -0
  110. package/dist/devtools/rewriteTunables.js +276 -0
  111. package/dist/devtools/saveEndpoint.d.ts +46 -0
  112. package/dist/devtools/saveEndpoint.js +48 -0
  113. package/dist/devtools/transformTunables.d.ts +3 -0
  114. package/dist/devtools/transformTunables.js +3 -0
  115. package/dist/devtools/tunableSchema.d.ts +31 -0
  116. package/dist/devtools/tunableSchema.js +31 -0
  117. package/dist/economy/currency.d.ts +12 -1
  118. package/dist/economy/currency.js +12 -1
  119. package/dist/economy/listingBook.d.ts +91 -0
  120. package/dist/economy/listingBook.js +144 -0
  121. package/dist/economy/resourceLedger.d.ts +222 -0
  122. package/dist/economy/resourceLedger.js +353 -0
  123. package/dist/economy/sharedWallet.d.ts +14 -0
  124. package/dist/economy/sharedWallet.js +14 -0
  125. package/dist/economy/techTree.d.ts +12 -0
  126. package/dist/economy/techTree.js +12 -0
  127. package/dist/economy/wallet.d.ts +26 -2
  128. package/dist/economy/wallet.js +35 -6
  129. package/dist/editor/commands.d.ts +248 -0
  130. package/dist/editor/commands.js +865 -0
  131. package/dist/editor/document.d.ts +186 -0
  132. package/dist/editor/document.js +884 -0
  133. package/dist/editor/grid.d.ts +229 -0
  134. package/dist/editor/grid.js +366 -0
  135. package/dist/editor/gridAdapters.d.ts +80 -0
  136. package/dist/editor/gridAdapters.js +134 -0
  137. package/dist/editor/index.d.ts +97 -0
  138. package/dist/editor/index.js +10 -0
  139. package/dist/editor/liveSync.d.ts +127 -0
  140. package/dist/editor/liveSync.js +249 -0
  141. package/dist/editor/runtimeInspector.d.ts +88 -0
  142. package/dist/editor/runtimeInspector.js +239 -0
  143. package/dist/editor/types.d.ts +175 -0
  144. package/dist/editor/types.js +29 -0
  145. package/dist/faction/reputation.d.ts +5 -0
  146. package/dist/faction/reputation.js +5 -0
  147. package/dist/format/distance.d.ts +17 -0
  148. package/dist/format/distance.js +18 -0
  149. package/dist/format/duration.d.ts +27 -0
  150. package/dist/format/duration.js +45 -0
  151. package/dist/format/speed.d.ts +17 -0
  152. package/dist/format/speed.js +25 -0
  153. package/dist/game/connectedPlayers.d.ts +30 -0
  154. package/dist/game/connectedPlayers.js +21 -0
  155. package/dist/game/cosmetics.d.ts +9 -0
  156. package/dist/game/cosmetics.js +16 -0
  157. package/dist/game/defineGame.d.ts +141 -2
  158. package/dist/game/defineGame.js +39 -1
  159. package/dist/game/defineSystem.d.ts +88 -0
  160. package/dist/game/defineSystem.js +45 -0
  161. package/dist/game/dialogue.d.ts +33 -0
  162. package/dist/game/dialogue.js +21 -0
  163. package/dist/game/events.d.ts +50 -13
  164. package/dist/game/events.js +5 -0
  165. package/dist/game/feed.d.ts +33 -0
  166. package/dist/game/feed.js +35 -2
  167. package/dist/game/gamePhase.d.ts +11 -0
  168. package/dist/game/gamePhase.js +16 -0
  169. package/dist/game/keyValueStore.d.ts +25 -0
  170. package/dist/game/keyValueStore.js +61 -0
  171. package/dist/game/leaderboard.d.ts +5 -0
  172. package/dist/game/leaderboard.js +5 -0
  173. package/dist/game/levelSequence.d.ts +24 -2
  174. package/dist/game/levelSequence.js +51 -2
  175. package/dist/game/loadout.d.ts +5 -0
  176. package/dist/game/loadout.js +5 -0
  177. package/dist/game/lootFilter.d.ts +2 -0
  178. package/dist/game/lootFilter.js +2 -0
  179. package/dist/game/lootPipeline.d.ts +164 -0
  180. package/dist/game/lootPipeline.js +216 -0
  181. package/dist/game/lootTable.d.ts +21 -0
  182. package/dist/game/lootTable.js +15 -4
  183. package/dist/game/modelAnimation.d.ts +8 -0
  184. package/dist/game/modelAnimation.js +18 -0
  185. package/dist/game/objectives.d.ts +43 -0
  186. package/dist/game/objectives.js +36 -0
  187. package/dist/game/paramLayers.d.ts +148 -0
  188. package/dist/game/paramLayers.js +185 -0
  189. package/dist/game/ping.d.ts +5 -0
  190. package/dist/game/ping.js +5 -0
  191. package/dist/game/playableGame.d.ts +160 -12
  192. package/dist/game/quest.d.ts +8 -0
  193. package/dist/game/quest.js +29 -0
  194. package/dist/game/race.d.ts +141 -0
  195. package/dist/game/race.js +169 -0
  196. package/dist/game/recordBook.d.ts +5 -5
  197. package/dist/game/recordBook.js +4 -1
  198. package/dist/game/ruleSelection.d.ts +75 -0
  199. package/dist/game/ruleSelection.js +127 -0
  200. package/dist/game/runDraft.d.ts +5 -0
  201. package/dist/game/runDraft.js +5 -0
  202. package/dist/game/saveStore.d.ts +111 -0
  203. package/dist/game/saveStore.js +312 -0
  204. package/dist/game/snapshotHistory.d.ts +67 -0
  205. package/dist/game/snapshotHistory.js +95 -0
  206. package/dist/game/social.d.ts +38 -1
  207. package/dist/game/social.js +71 -0
  208. package/dist/game/spawnPoints.d.ts +5 -0
  209. package/dist/game/spawnPoints.js +5 -0
  210. package/dist/game/systemRuntime.d.ts +50 -0
  211. package/dist/game/systemRuntime.js +157 -0
  212. package/dist/game/systemSchedule.d.ts +72 -0
  213. package/dist/game/systemSchedule.js +242 -0
  214. package/dist/game/toasts.d.ts +43 -0
  215. package/dist/game/toasts.js +44 -0
  216. package/dist/game/trade.d.ts +10 -0
  217. package/dist/game/trade.js +10 -0
  218. package/dist/game/unlocks.d.ts +8 -0
  219. package/dist/game/unlocks.js +16 -0
  220. package/dist/game/vfxInstance.d.ts +138 -0
  221. package/dist/game/vfxInstance.js +96 -0
  222. package/dist/game/worldItem.d.ts +17 -4
  223. package/dist/game/worldItem.js +17 -4
  224. package/dist/gameplay.d.ts +91 -0
  225. package/dist/gameplay.js +91 -0
  226. package/dist/index.d.ts +5 -7
  227. package/dist/index.js +5 -7
  228. package/dist/input/actionBindings.d.ts +24 -5
  229. package/dist/input/actionBindings.js +23 -5
  230. package/dist/input/axisInput.d.ts +13 -1
  231. package/dist/input/axisInput.js +22 -1
  232. package/dist/input/controlGroups.d.ts +67 -0
  233. package/dist/input/controlGroups.js +41 -0
  234. package/dist/input/touchScheme.d.ts +82 -6
  235. package/dist/input/touchScheme.js +123 -10
  236. package/dist/interaction/contextMenu.d.ts +1 -0
  237. package/dist/interaction/contextMenu.js +1 -0
  238. package/dist/interaction/lockpick.d.ts +61 -0
  239. package/dist/interaction/lockpick.js +168 -0
  240. package/dist/interaction/proximityPrompt.d.ts +5 -1
  241. package/dist/interaction/proximityPrompt.js +5 -3
  242. package/dist/interaction/qte.d.ts +5 -0
  243. package/dist/interaction/qte.js +5 -0
  244. package/dist/interaction/skillCheck.d.ts +5 -0
  245. package/dist/interaction/skillCheck.js +5 -0
  246. package/dist/inventory/inventoryModel.d.ts +12 -0
  247. package/dist/inventory/inventoryModel.js +12 -0
  248. package/dist/inventory/shapedGrid.d.ts +16 -0
  249. package/dist/inventory/shapedGrid.js +16 -0
  250. package/dist/inventory/slotModel.d.ts +10 -0
  251. package/dist/inventory/slotModel.js +10 -0
  252. package/dist/item/durability.d.ts +5 -0
  253. package/dist/item/durability.js +5 -0
  254. package/dist/item/itemIdentity.d.ts +171 -0
  255. package/dist/item/itemIdentity.js +138 -0
  256. package/dist/item/itemInstanceRegistry.d.ts +32 -0
  257. package/dist/item/itemInstanceRegistry.js +34 -0
  258. package/dist/item/itemgen.d.ts +163 -0
  259. package/dist/item/itemgen.js +151 -0
  260. package/dist/item/modularItem.d.ts +5 -0
  261. package/dist/item/modularItem.js +5 -0
  262. package/dist/item/use.d.ts +5 -0
  263. package/dist/item/use.js +5 -0
  264. package/dist/item/useBehavior.d.ts +142 -0
  265. package/dist/item/useBehavior.js +105 -0
  266. package/dist/item/weapon.d.ts +5 -0
  267. package/dist/item/weapon.js +5 -0
  268. package/dist/math/scalar.d.ts +25 -0
  269. package/dist/math/scalar.js +47 -0
  270. package/dist/meta/changelog.d.ts +4 -1
  271. package/dist/meta/changelog.js +36 -1
  272. package/dist/movement/avoidance.d.ts +45 -0
  273. package/dist/movement/avoidance.js +123 -0
  274. package/dist/movement/cameraRig.d.ts +8 -0
  275. package/dist/movement/cameraRig.js +8 -0
  276. package/dist/movement/dash.d.ts +11 -0
  277. package/dist/movement/dash.js +11 -0
  278. package/dist/movement/formation.d.ts +135 -0
  279. package/dist/movement/formation.js +194 -0
  280. package/dist/movement/glideModel.d.ts +5 -0
  281. package/dist/movement/glideModel.js +5 -0
  282. package/dist/movement/grappleSwing.d.ts +5 -0
  283. package/dist/movement/grappleSwing.js +5 -0
  284. package/dist/movement/leaderTrail.d.ts +5 -0
  285. package/dist/movement/leaderTrail.js +5 -0
  286. package/dist/movement/movementModel.d.ts +38 -7
  287. package/dist/movement/movementModel.js +54 -13
  288. package/dist/movement/playerMovement.d.ts +41 -0
  289. package/dist/movement/playerMovement.js +236 -0
  290. package/dist/movement/poseState.d.ts +13 -0
  291. package/dist/movement/poseState.js +16 -0
  292. package/dist/movement/steering.d.ts +8 -0
  293. package/dist/movement/steering.js +18 -0
  294. package/dist/multiplayer/combatSnapshot.d.ts +3 -0
  295. package/dist/multiplayer/combatSnapshot.js +3 -0
  296. package/dist/multiplayer/lagCompensation.d.ts +5 -0
  297. package/dist/multiplayer/lagCompensation.js +5 -0
  298. package/dist/multiplayer/presenceModel.d.ts +9 -1
  299. package/dist/multiplayer/presenceModel.js +9 -1
  300. package/dist/multiplayer/simultaneousCommit.d.ts +3 -0
  301. package/dist/multiplayer/simultaneousCommit.js +3 -0
  302. package/dist/multiplayer.d.ts +11 -0
  303. package/dist/multiplayer.js +11 -0
  304. package/dist/nav/pathFollow.d.ts +57 -0
  305. package/dist/nav/pathFollow.js +109 -0
  306. package/dist/orders/orderKinds.d.ts +156 -0
  307. package/dist/orders/orderKinds.js +197 -0
  308. package/dist/orders/orderQueue.d.ts +208 -0
  309. package/dist/orders/orderQueue.js +211 -0
  310. package/dist/physics/drivableVehicle.d.ts +29 -0
  311. package/dist/physics/drivableVehicle.js +16 -0
  312. package/dist/physics/kinematicVehicle.d.ts +21 -1
  313. package/dist/physics/kinematicVehicle.js +23 -8
  314. package/dist/physics/physicsWorld.d.ts +24 -12
  315. package/dist/physics/physicsWorld.js +11 -5
  316. package/dist/physics/radialImpulse.d.ts +25 -0
  317. package/dist/physics/radialImpulse.js +27 -0
  318. package/dist/procedural.d.ts +3 -0
  319. package/dist/procedural.js +3 -0
  320. package/dist/progression/statGraph.d.ts +116 -0
  321. package/dist/progression/statGraph.js +318 -0
  322. package/dist/puzzle/cellGrid.d.ts +9 -0
  323. package/dist/puzzle/cellGrid.js +9 -0
  324. package/dist/puzzle/fallingPiece.d.ts +9 -0
  325. package/dist/puzzle/fallingPiece.js +9 -0
  326. package/dist/puzzle/nonogram.d.ts +39 -0
  327. package/dist/puzzle/nonogram.js +136 -0
  328. package/dist/random/nameGen.d.ts +5 -0
  329. package/dist/random/nameGen.js +5 -0
  330. package/dist/random/pick.d.ts +8 -0
  331. package/dist/random/pick.js +31 -0
  332. package/dist/random/rng.d.ts +24 -0
  333. package/dist/random/rng.js +30 -8
  334. package/dist/random/seedLink.d.ts +4 -0
  335. package/dist/random/seedLink.js +4 -0
  336. package/dist/relation/keyedValues.d.ts +54 -0
  337. package/dist/relation/keyedValues.js +115 -0
  338. package/dist/relation/thresholds.d.ts +62 -0
  339. package/dist/relation/thresholds.js +62 -0
  340. package/dist/render/color.d.ts +12 -0
  341. package/dist/render/color.js +26 -0
  342. package/dist/render/lookPreset.d.ts +41 -0
  343. package/dist/render/lookPreset.js +29 -0
  344. package/dist/render/postProcessing.d.ts +76 -0
  345. package/dist/render/postProcessing.js +21 -0
  346. package/dist/rules/predicate.d.ts +53 -0
  347. package/dist/rules/predicate.js +64 -0
  348. package/dist/rules/ruleEffects.d.ts +38 -0
  349. package/dist/rules/ruleEffects.js +37 -0
  350. package/dist/rules/triggeredRules.d.ts +160 -0
  351. package/dist/rules/triggeredRules.js +241 -0
  352. package/dist/runtime/adapter.d.ts +58 -0
  353. package/dist/runtime/adapter.js +54 -5
  354. package/dist/runtime/cameraDirector.d.ts +1 -0
  355. package/dist/runtime/cameraDirector.js +1 -0
  356. package/dist/runtime/commandRunner.d.ts +1 -0
  357. package/dist/runtime/commandRunner.js +1 -0
  358. package/dist/runtime/context/combatFx.d.ts +23 -0
  359. package/dist/runtime/context/combatFx.js +161 -0
  360. package/dist/runtime/context/registries.d.ts +13 -0
  361. package/dist/runtime/context/registries.js +84 -0
  362. package/dist/runtime/context/worldItems.d.ts +21 -0
  363. package/dist/runtime/context/worldItems.js +37 -0
  364. package/dist/runtime/descriptors/baseline.d.ts +48 -0
  365. package/dist/runtime/descriptors/baseline.js +134 -0
  366. package/dist/runtime/descriptors/features.d.ts +74 -0
  367. package/dist/runtime/descriptors/features.js +281 -0
  368. package/dist/runtime/gameContext.d.ts +163 -19
  369. package/dist/runtime/gameContext.js +385 -339
  370. package/dist/runtime/gameRuntime.d.ts +1 -0
  371. package/dist/runtime/gameRuntime.js +1 -0
  372. package/dist/runtime/headlessRunner.d.ts +60 -0
  373. package/dist/runtime/headlessRunner.js +44 -0
  374. package/dist/runtime/hostPersistence.d.ts +12 -0
  375. package/dist/runtime/hostPersistence.js +12 -0
  376. package/dist/runtime/hostedGameRunner.d.ts +54 -0
  377. package/dist/runtime/hostedGameRunner.js +85 -0
  378. package/dist/runtime/hostedWorldSession.d.ts +73 -0
  379. package/dist/runtime/hostedWorldSession.js +64 -0
  380. package/dist/runtime/inputSnapshot.d.ts +21 -3
  381. package/dist/runtime/inputSnapshot.js +8 -2
  382. package/dist/runtime/motionIntents.d.ts +12 -1
  383. package/dist/runtime/motionIntents.js +26 -1
  384. package/dist/runtime/perContext.d.ts +15 -0
  385. package/dist/runtime/perContext.js +21 -0
  386. package/dist/runtime/runtimeSave.d.ts +79 -0
  387. package/dist/runtime/runtimeSave.js +105 -0
  388. package/dist/runtime/save.d.ts +4 -0
  389. package/dist/runtime/save.js +4 -0
  390. package/dist/runtime/snapshot.d.ts +7 -0
  391. package/dist/runtime/snapshot.js +7 -0
  392. package/dist/runtime/visibility.d.ts +2 -1
  393. package/dist/runtime/visibility.js +2 -1
  394. package/dist/runtime/worldChannel.d.ts +62 -0
  395. package/dist/runtime/worldChannel.js +114 -0
  396. package/dist/runtime/worldMirror.d.ts +36 -0
  397. package/dist/runtime/worldMirror.js +44 -0
  398. package/dist/runtime/worldProjection.d.ts +47 -0
  399. package/dist/runtime/worldProjection.js +52 -0
  400. package/dist/runtime/worldReplication.d.ts +69 -0
  401. package/dist/runtime/worldReplication.js +217 -0
  402. package/dist/runtime/worldSnapshot.d.ts +44 -0
  403. package/dist/runtime/worldSnapshot.js +30 -0
  404. package/dist/scene/assetCatalog.d.ts +22 -0
  405. package/dist/scene/assetCatalog.js +4 -0
  406. package/dist/scene/assetDiagnostics.d.ts +69 -0
  407. package/dist/scene/assetDiagnostics.js +110 -0
  408. package/dist/scene/assetGenerator.d.ts +65 -0
  409. package/dist/scene/assetGenerator.js +64 -0
  410. package/dist/scene/assetSpace.d.ts +137 -0
  411. package/dist/scene/assetSpace.js +259 -0
  412. package/dist/scene/authoredTriggers.d.ts +169 -0
  413. package/dist/scene/authoredTriggers.js +340 -0
  414. package/dist/scene/behaviorRuntime.d.ts +75 -0
  415. package/dist/scene/behaviorRuntime.js +217 -0
  416. package/dist/scene/behaviors.d.ts +14 -2
  417. package/dist/scene/behaviors.js +7 -2
  418. package/dist/scene/bodyBind.d.ts +60 -0
  419. package/dist/scene/bodyBind.js +51 -0
  420. package/dist/scene/builtinSceneKinds.d.ts +5 -0
  421. package/dist/scene/builtinSceneKinds.js +62 -0
  422. package/dist/scene/colliders.d.ts +18 -0
  423. package/dist/scene/colliders.js +61 -1
  424. package/dist/scene/entityStats.d.ts +13 -0
  425. package/dist/scene/entityStats.js +30 -0
  426. package/dist/scene/entityStore.d.ts +41 -1
  427. package/dist/scene/entityStore.js +75 -0
  428. package/dist/scene/facing.d.ts +18 -0
  429. package/dist/scene/facing.js +26 -0
  430. package/dist/scene/modelSockets.d.ts +33 -0
  431. package/dist/scene/modelSockets.js +29 -0
  432. package/dist/scene/objectQuery.d.ts +2 -0
  433. package/dist/scene/objectQuery.js +2 -0
  434. package/dist/scene/objectStore.d.ts +4 -0
  435. package/dist/scene/objectStore.js +6 -0
  436. package/dist/scene/possession.d.ts +8 -0
  437. package/dist/scene/possession.js +14 -0
  438. package/dist/scene/roster.d.ts +3 -0
  439. package/dist/scene/roster.js +12 -0
  440. package/dist/scene/sceneKinds.d.ts +240 -0
  441. package/dist/scene/sceneKinds.js +214 -0
  442. package/dist/scene/sceneOwnership.d.ts +169 -0
  443. package/dist/scene/sceneOwnership.js +179 -0
  444. package/dist/scene/selectionBookmarks.d.ts +93 -0
  445. package/dist/scene/selectionBookmarks.js +122 -0
  446. package/dist/scene/vehicleSeat.d.ts +68 -0
  447. package/dist/scene/vehicleSeat.js +59 -0
  448. package/dist/sensor/concealment.d.ts +3 -0
  449. package/dist/sensor/concealment.js +3 -0
  450. package/dist/sensor/freezeMonitor.d.ts +1 -0
  451. package/dist/sensor/freezeMonitor.js +1 -0
  452. package/dist/sensor/frustumSensor.d.ts +7 -3
  453. package/dist/sensor/frustumSensor.js +7 -3
  454. package/dist/sensor/hiddenStateProbe.d.ts +5 -2
  455. package/dist/sensor/hiddenStateProbe.js +5 -2
  456. package/dist/sensor/recordingBuffer.d.ts +2 -1
  457. package/dist/sensor/recordingBuffer.js +2 -1
  458. package/dist/sensor/replayLoop.d.ts +6 -2
  459. package/dist/sensor/replayLoop.js +6 -2
  460. package/dist/sensor/revealQuery.d.ts +2 -1
  461. package/dist/sensor/revealQuery.js +2 -1
  462. package/dist/sensor/visionCone.d.ts +10 -3
  463. package/dist/sensor/visionCone.js +10 -3
  464. package/dist/session/contestedChannel.d.ts +1 -0
  465. package/dist/session/contestedChannel.js +1 -0
  466. package/dist/session/extraction.d.ts +1 -0
  467. package/dist/session/extraction.js +1 -0
  468. package/dist/session/roles.d.ts +6 -0
  469. package/dist/session/roles.js +6 -0
  470. package/dist/session/roundState.d.ts +8 -0
  471. package/dist/session/roundState.js +2 -0
  472. package/dist/settings/settingsModel.d.ts +1 -0
  473. package/dist/settings/settingsModel.js +1 -0
  474. package/dist/stats/accumulatorMeter.d.ts +6 -0
  475. package/dist/stats/accumulatorMeter.js +6 -0
  476. package/dist/stats/eventMeter.d.ts +5 -0
  477. package/dist/stats/eventMeter.js +5 -0
  478. package/dist/stats/rollCheck.d.ts +5 -0
  479. package/dist/stats/rollCheck.js +5 -0
  480. package/dist/stats/statModifiers.d.ts +5 -0
  481. package/dist/stats/statModifiers.js +5 -0
  482. package/dist/store/defineKeyedStore.d.ts +38 -0
  483. package/dist/store/defineKeyedStore.js +42 -0
  484. package/dist/store/defineStore.d.ts +33 -0
  485. package/dist/store/defineStore.js +35 -0
  486. package/dist/store/observableKeyedStore.d.ts +9 -0
  487. package/dist/store/observableKeyedStore.js +43 -2
  488. package/dist/survival/decayMeter.d.ts +55 -0
  489. package/dist/survival/decayMeter.js +130 -55
  490. package/dist/survival/moodle.d.ts +2 -0
  491. package/dist/survival/regionHealth.d.ts +6 -0
  492. package/dist/survival/regionHealth.js +5 -0
  493. package/dist/tactics/fallingGrid.d.ts +6 -4
  494. package/dist/tactics/fallingGrid.js +6 -4
  495. package/dist/tactics/predictiveQuery.d.ts +3 -0
  496. package/dist/tactics/predictiveQuery.js +3 -0
  497. package/dist/tactics/snapshot.d.ts +2 -0
  498. package/dist/tactics/snapshot.js +2 -0
  499. package/dist/tactics/surface.d.ts +1 -0
  500. package/dist/tactics/surface.js +1 -0
  501. package/dist/tactics/tacticalGrid.d.ts +1 -0
  502. package/dist/tactics/tacticalGrid.js +1 -0
  503. package/dist/time/beatClock.d.ts +14 -4
  504. package/dist/time/beatClock.js +14 -4
  505. package/dist/time/calendarClock.d.ts +3 -0
  506. package/dist/time/calendarClock.js +3 -0
  507. package/dist/time/idleProgress.d.ts +4 -0
  508. package/dist/time/idleProgress.js +4 -0
  509. package/dist/time/simClock.d.ts +2 -0
  510. package/dist/time/simClock.js +20 -5
  511. package/dist/ui/actionModel.d.ts +110 -0
  512. package/dist/ui/actionModel.js +159 -0
  513. package/dist/ui/gameLayout.d.ts +144 -0
  514. package/dist/ui/gameLayout.js +148 -0
  515. package/dist/ui/hudDocument.d.ts +114 -0
  516. package/dist/ui/hudDocument.js +220 -0
  517. package/dist/ui/hudLayout.d.ts +33 -1
  518. package/dist/ui/hudLayout.js +204 -17
  519. package/dist/ui/orientation.d.ts +39 -0
  520. package/dist/ui/orientation.js +49 -0
  521. package/dist/ui/selectionModel.d.ts +92 -0
  522. package/dist/ui/selectionModel.js +88 -0
  523. package/dist/ui/swingTimer.d.ts +42 -0
  524. package/dist/ui/swingTimer.js +38 -0
  525. package/dist/ui/tooltipModel.d.ts +63 -0
  526. package/dist/ui/tooltipModel.js +82 -0
  527. package/dist/ui.d.ts +15 -0
  528. package/dist/ui.js +15 -0
  529. package/dist/visibility/bounds.d.ts +8 -1
  530. package/dist/visibility/bounds.js +8 -1
  531. package/dist/visibility/frustum.d.ts +12 -3
  532. package/dist/visibility/frustum.js +12 -3
  533. package/dist/visibility/spatialIndex.js +34 -20
  534. package/dist/work/jobQueue.d.ts +201 -0
  535. package/dist/work/jobQueue.js +253 -0
  536. package/dist/work/unitTraining.d.ts +58 -0
  537. package/dist/work/unitTraining.js +52 -0
  538. package/dist/world/authoredObjects.d.ts +58 -0
  539. package/dist/world/authoredObjects.js +69 -0
  540. package/dist/world/buildingGenerator.d.ts +18 -0
  541. package/dist/world/buildingGenerator.js +62 -0
  542. package/dist/world/buildings.d.ts +5 -0
  543. package/dist/world/buildings.js +5 -0
  544. package/dist/world/catenary.d.ts +22 -0
  545. package/dist/world/catenary.js +69 -0
  546. package/dist/world/environmentSummary.d.ts +11 -2
  547. package/dist/world/environmentSummary.js +11 -1
  548. package/dist/world/features.d.ts +244 -7
  549. package/dist/world/features.js +92 -4
  550. package/dist/world/footprintGrid.d.ts +59 -0
  551. package/dist/world/footprintGrid.js +141 -0
  552. package/dist/world/geometry.d.ts +64 -0
  553. package/dist/world/geometry.js +94 -0
  554. package/dist/world/grassKind.d.ts +51 -0
  555. package/dist/world/grassKind.js +101 -0
  556. package/dist/world/pathInstances.d.ts +27 -0
  557. package/dist/world/pathInstances.js +27 -0
  558. package/dist/world/pathTerrain.d.ts +80 -0
  559. package/dist/world/pathTerrain.js +142 -0
  560. package/dist/world/placeAsset.d.ts +81 -0
  561. package/dist/world/placeAsset.js +77 -0
  562. package/dist/world/placement.d.ts +4 -0
  563. package/dist/world/placement.js +4 -0
  564. package/dist/world/placementController.d.ts +6 -0
  565. package/dist/world/placementController.js +6 -0
  566. package/dist/world/polyline.d.ts +34 -0
  567. package/dist/world/polyline.js +81 -0
  568. package/dist/world/roads.d.ts +55 -0
  569. package/dist/world/roads.js +184 -0
  570. package/dist/world/scatterRegion.d.ts +164 -0
  571. package/dist/world/scatterRegion.js +409 -0
  572. package/dist/world/sceneShapes.d.ts +43 -0
  573. package/dist/world/sceneShapes.js +1 -0
  574. package/dist/world/segment.d.ts +27 -0
  575. package/dist/world/segment.js +43 -0
  576. package/dist/world/soilKind.d.ts +48 -0
  577. package/dist/world/soilKind.js +92 -0
  578. package/dist/world/spatialSample.d.ts +241 -0
  579. package/dist/world/spatialSample.js +465 -0
  580. package/dist/world/streets.d.ts +80 -0
  581. package/dist/world/streets.js +144 -0
  582. package/dist/world/terraform.d.ts +213 -1
  583. package/dist/world/terraform.js +655 -20
  584. package/dist/world/terrain.d.ts +138 -12
  585. package/dist/world/terrain.js +346 -28
  586. package/dist/world/terrainGuides.d.ts +182 -0
  587. package/dist/world/terrainGuides.js +343 -0
  588. package/dist/world/vec2.d.ts +81 -0
  589. package/dist/world/vec2.js +128 -0
  590. package/dist/world/vec3.d.ts +49 -0
  591. package/dist/world/vec3.js +76 -0
  592. package/dist/world/vegetation.d.ts +71 -0
  593. package/dist/world/vegetation.js +151 -0
  594. package/dist/world/visibilityField.d.ts +154 -0
  595. package/dist/world/visibilityField.js +271 -0
  596. package/dist/world/volumetricClouds.d.ts +52 -0
  597. package/dist/world/volumetricClouds.js +43 -0
  598. package/dist/world/walls.d.ts +9 -0
  599. package/dist/world/walls.js +9 -0
  600. package/dist/world/waterKind.d.ts +55 -0
  601. package/dist/world/waterKind.js +99 -0
  602. package/dist/world.d.ts +132 -0
  603. package/dist/world.js +132 -0
  604. package/package.json +32 -8
  605. package/skills/jgengine/SKILL.md +51 -0
  606. package/skills/jgengine/api.md +434 -0
  607. package/skills/jgengine/capabilities.md +29 -0
  608. package/skills/jgengine/reference-cartridge.md +72 -0
  609. package/skills/jgengine-combat/SKILL.md +34 -0
  610. package/skills/jgengine-combat/api.md +549 -0
  611. package/skills/jgengine-combat/capabilities.md +169 -0
  612. package/skills/jgengine-combat/reference.md +98 -0
  613. package/skills/jgengine-gameplay/SKILL.md +39 -0
  614. package/skills/jgengine-gameplay/api.md +1794 -0
  615. package/skills/jgengine-gameplay/capabilities.md +378 -0
  616. package/skills/jgengine-gameplay/reference-systems.md +60 -0
  617. package/skills/jgengine-world/SKILL.md +38 -0
  618. package/skills/jgengine-world/api.md +2652 -0
  619. package/skills/jgengine-world/capabilities.md +370 -0
  620. package/skills/jgengine-world/reference.md +222 -0
  621. package/dist/cartridge/runtime.d.ts +0 -15
  622. package/dist/cartridge/runtime.js +0 -556
  623. package/dist/cartridge/spec.d.ts +0 -188
  624. package/dist/cartridge/spec.js +0 -19
  625. package/dist/cartridge/validate.d.ts +0 -2
  626. package/dist/cartridge/validate.js +0 -78
  627. package/dist/store/engineStore.d.ts +0 -22
  628. package/dist/store/engineStore.js +0 -50
  629. package/dist/store/features.d.ts +0 -10
  630. package/dist/store/features.js +0 -23
  631. package/llms.txt +0 -4983
@@ -0,0 +1,194 @@
1
+ /**
2
+ * Group destination assignment: slot a moving group into a formation around a
3
+ * target point, then match members to slots. Shape is caller data — a
4
+ * {@link FormationSlotGenerator} emits slot offsets in the group's local frame
5
+ * ("right" = +x, "forward" = +y) and the engine ships line/box/wedge/circle
6
+ * only as samples; a custom generator needs no engine change. Placement and
7
+ * matching are pure and deterministic so the same inputs always yield the same
8
+ * world slots and the same assignment, which keeps them replay- and
9
+ * network-safe. Route planning and local collision avoidance are deliberately
10
+ * separate seams (`movement/avoidance`, `nav/pathFollow`): this module answers
11
+ * only "where should each member stand", not "how does it get there".
12
+ */
13
+ import { yawForward, yawRight } from "./steering.js";
14
+ /**
15
+ * Engine yaw (`rotationY`, radians) that faces from `from` toward `to` on the
16
+ * XZ plane, matching the `forward = (sin yaw, cos yaw)` convention. Feed the
17
+ * result as the `facing` of {@link placeFormation} to orient a formation along
18
+ * its travel direction. Returns `0` when the points coincide.
19
+ *
20
+ * @capability formation-facing group facing yaw from a travel direction on the XZ plane
21
+ * @consumer squad and crowd movement — orient a destination formation along its heading
22
+ */
23
+ export function facingYaw(from, to) {
24
+ const dx = to[0] - from[0];
25
+ const dz = to[1] - from[1];
26
+ if (dx * dx + dz * dz <= 1e-18)
27
+ return 0;
28
+ return Math.atan2(dx, dz);
29
+ }
30
+ /**
31
+ * Transform a generator's local slot offsets into world XZ positions around a
32
+ * `destination`, rotated by `facing` (engine yaw). Slot `i` in the returned
33
+ * array is `generator(count)[i]` mapped through the group frame, so it stays
34
+ * aligned with {@link assignFormationSlots}' slot indices. Pure and allocation-
35
+ * light: one array of `count` points, no per-call closures retained.
36
+ *
37
+ * @capability formation-placement place a group formation's world slots around a destination
38
+ * @consumer squad/party/convoy movement — generate per-member destination slots around a target
39
+ */
40
+ export function placeFormation(destination, facing, count, generator) {
41
+ if (count <= 0)
42
+ return [];
43
+ const forward = yawForward(facing);
44
+ const right = yawRight(facing);
45
+ const local = generator(count);
46
+ const slots = [];
47
+ for (let i = 0; i < count; i += 1) {
48
+ const offset = local[i] ?? ZERO;
49
+ const r = offset[0];
50
+ const f = offset[1];
51
+ slots.push([
52
+ destination[0] + right[0] * r + forward[0] * f,
53
+ destination[1] + right[1] * r + forward[1] * f,
54
+ ]);
55
+ }
56
+ return slots;
57
+ }
58
+ /**
59
+ * Match `members` to `slots` by a deterministic greedy nearest assignment:
60
+ * every (member, slot) pair is ranked by squared travel distance (minus a
61
+ * stickiness bonus for a member's previous slot) and assigned in order while
62
+ * both ends are free. Returns `assignment[member] = slot`, or `-1` for members
63
+ * left unmatched when there are fewer slots than members. Ties break by member
64
+ * then slot index, so the result is stable across runs and independent of input
65
+ * ordering — the property replay and lockstep multiplayer rely on. Groups are
66
+ * bounded, so the `O(members·slots·log)` sort is fine; this is not a per-frame
67
+ * whole-world pass.
68
+ *
69
+ * @capability formation-assignment stable deterministic member-to-slot matching for a group formation
70
+ * @consumer squad/party movement — assign each member a destination slot with low reshuffle churn
71
+ */
72
+ export function assignFormationSlots(members, slots, options = {}) {
73
+ const memberCount = members.length;
74
+ const slotCount = slots.length;
75
+ const assignment = new Array(memberCount).fill(-1);
76
+ if (memberCount === 0 || slotCount === 0)
77
+ return assignment;
78
+ const previous = options.previous;
79
+ const stickiness = options.stickiness ?? 0;
80
+ const pairs = [];
81
+ for (let m = 0; m < memberCount; m += 1) {
82
+ const member = members[m];
83
+ const keepSlot = previous?.[m];
84
+ for (let s = 0; s < slotCount; s += 1) {
85
+ const slot = slots[s];
86
+ const dx = slot[0] - member[0];
87
+ const dz = slot[1] - member[1];
88
+ let cost = dx * dx + dz * dz;
89
+ if (stickiness > 0 && keepSlot === s)
90
+ cost -= stickiness;
91
+ pairs.push({ member: m, slot: s, cost });
92
+ }
93
+ }
94
+ pairs.sort((a, b) => a.cost !== b.cost ? a.cost - b.cost : a.member !== b.member ? a.member - b.member : a.slot - b.slot);
95
+ const slotTaken = new Array(slotCount).fill(false);
96
+ let filled = 0;
97
+ const need = Math.min(memberCount, slotCount);
98
+ for (let p = 0; p < pairs.length && filled < need; p += 1) {
99
+ const pair = pairs[p];
100
+ if (assignment[pair.member] !== -1 || slotTaken[pair.slot])
101
+ continue;
102
+ assignment[pair.member] = pair.slot;
103
+ slotTaken[pair.slot] = true;
104
+ filled += 1;
105
+ }
106
+ return assignment;
107
+ }
108
+ const ZERO = [0, 0];
109
+ /**
110
+ * A single rank abreast, centered on the destination and facing forward — a
111
+ * skirmish line or a chorus row. Slots run left→right along the group's right
112
+ * axis.
113
+ *
114
+ * @capability formation-line line (abreast) slot generator for group destinations
115
+ * @consumer squad movement — line formation sample policy for {@link placeFormation}
116
+ */
117
+ export function lineFormation(options) {
118
+ const spacing = options.spacing;
119
+ return (count) => {
120
+ const slots = [];
121
+ const mid = (count - 1) / 2;
122
+ for (let i = 0; i < count; i += 1)
123
+ slots.push([(i - mid) * spacing, 0]);
124
+ return slots;
125
+ };
126
+ }
127
+ /**
128
+ * A rectangular grid centered on the destination, front row toward `+forward` —
129
+ * a marching block or a phalanx. Rows fill front-to-back, left-to-right.
130
+ *
131
+ * @capability formation-box box/grid slot generator for group destinations
132
+ * @consumer squad movement — box formation sample policy for {@link placeFormation}
133
+ */
134
+ export function boxFormation(options) {
135
+ const spacing = options.spacing;
136
+ const fixedColumns = options.columns;
137
+ return (count) => {
138
+ const columns = Math.max(1, fixedColumns ?? Math.ceil(Math.sqrt(count)));
139
+ const rows = Math.ceil(count / columns);
140
+ const midCol = (columns - 1) / 2;
141
+ const midRow = (rows - 1) / 2;
142
+ const slots = [];
143
+ for (let i = 0; i < count; i += 1) {
144
+ const row = Math.floor(i / columns);
145
+ const col = i % columns;
146
+ slots.push([(col - midCol) * spacing, (midRow - row) * spacing]);
147
+ }
148
+ return slots;
149
+ };
150
+ }
151
+ /**
152
+ * A "V"/arrowhead with the apex at the destination and arms trailing back — a
153
+ * flying-wedge charge or a goose skein. Slot 0 is the tip; later slots alternate
154
+ * right then left, each rank stepping one `spacing` outward and backward.
155
+ *
156
+ * @capability formation-wedge wedge/arrowhead slot generator for group destinations
157
+ * @consumer squad movement — wedge formation sample policy for {@link placeFormation}
158
+ */
159
+ export function wedgeFormation(options) {
160
+ const spacing = options.spacing;
161
+ return (count) => {
162
+ const slots = [];
163
+ for (let i = 0; i < count; i += 1) {
164
+ if (i === 0) {
165
+ slots.push([0, 0]);
166
+ continue;
167
+ }
168
+ const rank = Math.ceil(i / 2);
169
+ const side = i % 2 === 1 ? 1 : -1;
170
+ slots.push([side * rank * spacing, -rank * spacing]);
171
+ }
172
+ return slots;
173
+ };
174
+ }
175
+ /**
176
+ * An evenly spaced ring around the destination — a guard cordon, a huddle, or a
177
+ * surround. Slot 0 sits `startAngle` from forward; slots advance evenly around
178
+ * the circle.
179
+ *
180
+ * @capability formation-circle ring/cordon slot generator for group destinations
181
+ * @consumer squad/crowd movement — circle formation sample policy for {@link placeFormation}
182
+ */
183
+ export function circleFormation(options) {
184
+ const radius = options.radius;
185
+ const startAngle = options.startAngle ?? 0;
186
+ return (count) => {
187
+ const slots = [];
188
+ for (let i = 0; i < count; i += 1) {
189
+ const angle = startAngle + (2 * Math.PI * i) / count;
190
+ slots.push([radius * Math.sin(angle), radius * Math.cos(angle)]);
191
+ }
192
+ return slots;
193
+ };
194
+ }
@@ -41,4 +41,9 @@ export interface GlideModel {
41
41
  pose(): GlideStep;
42
42
  launch(position: GlideVec3, heading: number, initialSpeed?: number): void;
43
43
  }
44
+ /**
45
+ * Gliding/wingsuit descent control — lift, drag, and steering from a launch.
46
+ *
47
+ * @capability glide gliding/wingsuit descent control from a launch
48
+ */
44
49
  export declare function createGlideModel(config?: GlideModelConfig): GlideModel;
@@ -1,3 +1,8 @@
1
+ /**
2
+ * Gliding/wingsuit descent control — lift, drag, and steering from a launch.
3
+ *
4
+ * @capability glide gliding/wingsuit descent control from a launch
5
+ */
1
6
  export function createGlideModel(config = {}) {
2
7
  const gravity = (config.gravity ?? 20) * (config.gravityScale ?? 0.25);
3
8
  const thrustAccel = config.thrustAccel ?? 10;
@@ -31,4 +31,9 @@ export interface GrappleSwing {
31
31
  /** Constrain one frame. `reeling` shortens the rope; returns the corrected position/velocity. */
32
32
  step(position: SwingVec3, velocity: SwingVec3, dt: number, reeling?: boolean): GrappleSwingStep;
33
33
  }
34
+ /**
35
+ * Grappling-hook rope swing physics with anchor, pendulum motion, and reel-in.
36
+ *
37
+ * @capability grapple-swing grappling-hook rope swing physics with reel-in
38
+ */
34
39
  export declare function createGrappleSwing(config?: GrappleSwingConfig): GrappleSwing;
@@ -1,3 +1,8 @@
1
+ /**
2
+ * Grappling-hook rope swing physics with anchor, pendulum motion, and reel-in.
3
+ *
4
+ * @capability grapple-swing grappling-hook rope swing physics with reel-in
5
+ */
1
6
  export function createGrappleSwing(config = {}) {
2
7
  const reelSpeed = config.reelSpeed ?? 0;
3
8
  const minLength = config.minLength ?? 1;
@@ -26,4 +26,9 @@ export interface LeaderTrail {
26
26
  /** Drop all history (teleport, respawn) and optionally restart from a position. */
27
27
  reset(position?: TrailPoint): void;
28
28
  }
29
+ /**
30
+ * A trailing follower formation that chases a leader along its past path — snake/convoy trails.
31
+ *
32
+ * @capability follow-trail trailing follower/snake formation that chases a leader
33
+ */
29
34
  export declare function createLeaderTrail(config: LeaderTrailConfig): LeaderTrail;
@@ -1,3 +1,8 @@
1
+ /**
2
+ * A trailing follower formation that chases a leader along its past path — snake/convoy trails.
3
+ *
4
+ * @capability follow-trail trailing follower/snake formation that chases a leader
5
+ */
1
6
  export function createLeaderTrail(config) {
2
7
  if (!(config.spacing > 0))
3
8
  throw new Error(`leader trail spacing must be positive, got ${config.spacing}`);
@@ -12,6 +12,7 @@
12
12
  */
13
13
  export type MovementKey = "w" | "a" | "s" | "d" | "shift" | "control" | "c" | "space";
14
14
  export type MovementKeysState = Record<MovementKey, boolean>;
15
+ /** @internal */
15
16
  export declare function createEmptyMovementKeys(): MovementKeysState;
16
17
  /**
17
18
  * Frame-independent description of what the player is asking the avatar to do.
@@ -31,7 +32,8 @@ export interface MovementIntent {
31
32
  * Translate the set of held keys into an intent. When `canMove` is false (a
32
33
  * menu is open, the world is paused) the avatar is fully idle so it never
33
34
  * drifts behind an overlay.
34
- */
35
+ * @internal
36
+ */
35
37
  export declare function resolveMovementIntent(keys: MovementKeysState, canMove: boolean): MovementIntent;
36
38
  /**
37
39
  * Kinematics + feel tuning for the first-person controller. Centralised here so
@@ -43,6 +45,8 @@ export declare const MOVEMENT_TUNING: {
43
45
  readonly walkSpeedMultiplier: 1.75;
44
46
  readonly runSpeedMultiplier: 2.25;
45
47
  readonly crouchSpeedMultiplier: 0.45;
48
+ /** Backward (S) travels this fraction of walk speed so retreating reads slower than advancing. */
49
+ readonly backpedalSpeedMultiplier: 0.65;
46
50
  readonly groundAcceleration: 26;
47
51
  readonly airAcceleration: 12;
48
52
  readonly groundFriction: 18;
@@ -74,6 +78,7 @@ export interface PlayerMotionState {
74
78
  grounded: boolean;
75
79
  jumpHeld: boolean;
76
80
  }
81
+ /** @internal */
77
82
  export declare function createPlayerMotionState(): PlayerMotionState;
78
83
  /** Horizontal step (world units) the avatar should commit this frame. */
79
84
  export interface MovementFrameStep {
@@ -87,6 +92,19 @@ export interface MovementFrameStep {
87
92
  export interface MovementTuningOverrides {
88
93
  gravityAcceleration?: number;
89
94
  jumpVelocity?: number;
95
+ /** Fraction of walk speed while backpedalling; overrides {@link MOVEMENT_TUNING.backpedalSpeedMultiplier}. */
96
+ backpedalSpeedMultiplier?: number;
97
+ }
98
+ /**
99
+ * Per-frame dynamic modifiers for {@link advancePlayerMotion} — state the caller
100
+ * recomputes each tick (unlike the static {@link MovementTuningOverrides}). Omitted
101
+ * fields leave the integrator at its default behavior.
102
+ */
103
+ export interface MotionFrameOptions {
104
+ /** Extra multiplier applied on top of the resolved target speed (e.g. swimming). Default 1. */
105
+ speedScale?: number;
106
+ /** Suppress gravity/jump integration and hold the avatar afloat this frame (e.g. swimming). Default false. */
107
+ floating?: boolean;
90
108
  }
91
109
  /**
92
110
  * Advance one frame of avatar kinematics. Mutates `motion` (velocity, jump,
@@ -97,8 +115,9 @@ export interface MovementTuningOverrides {
97
115
  * (need not be normalized); the avatar's right axis is derived from it. Pulling
98
116
  * this out of the render loop is what lets us assert "held forward for N frames
99
117
  * crosses the room" in a unit test instead of only in the live game.
100
- */
101
- export declare function advancePlayerMotion(motion: PlayerMotionState, intent: MovementIntent, forwardX: number, forwardZ: number, baseSpeed: number, rawDeltaSeconds: number, tuning?: MovementTuningOverrides): MovementFrameStep;
118
+ * @internal
119
+ */
120
+ export declare function advancePlayerMotion(motion: PlayerMotionState, intent: MovementIntent, forwardX: number, forwardZ: number, baseSpeed: number, rawDeltaSeconds: number, tuning?: MovementTuningOverrides, options?: MotionFrameOptions): MovementFrameStep;
102
121
  /** A placed scene object the walking player collides against as a circle-vs-AABB obstacle. */
103
122
  export interface CollisionObstacle {
104
123
  position: readonly [number, number, number];
@@ -113,17 +132,29 @@ export interface CollisionObstacle {
113
132
  * by `playerRadius`; an obstacle whose vertical span misses the player's
114
133
  * feet-to-head span is skipped entirely. Callers should pre-filter to nearby
115
134
  * objects — this also early-exits per obstacle on horizontal distance.
116
- */
135
+ * @internal
136
+ */
117
137
  export declare function resolveObstacleStep(current: readonly [number, number, number], stepX: number, stepZ: number, obstacles: readonly CollisionObstacle[], playerRadius?: number): MovementFrameStep;
118
- /** Zeroes the off-axis component so travel is locked to a single world axis (`PlayerMovementConfig.mode: "axis"`). */
138
+ /** Placed objects within `radius` (XZ) of `center`, as {@link CollisionObstacle}s to pre-filter for {@link resolveObstacleStep}.
139
+ * @internal
140
+ */
141
+ export declare function nearbyObstacles(objects: readonly {
142
+ position: readonly [number, number, number];
143
+ }[], center: readonly [number, number, number], radius?: number): CollisionObstacle[];
144
+ /** Zeroes the off-axis component so travel is locked to a single world axis (`PlayerMovementConfig.mode: "axis"`).
145
+ * @internal
146
+ */
119
147
  export declare function constrainStepToAxis(stepX: number, stepZ: number, axis: "x" | "z"): MovementFrameStep;
120
148
  /**
121
149
  * Snap a world position to its containing cell's center, matching the
122
150
  * bounds-free form of `navGrid`'s and `tacticalGrid`'s `floor` + half-cell
123
151
  * convention (`PlayerMovementConfig.mode: "grid"`).
124
- */
152
+ * @internal
153
+ */
125
154
  export declare function snapPositionToGrid(x: number, z: number, cellSize: number): [number, number];
126
155
  /** Peak jump height from MOVEMENT_TUNING.jumpVelocity + gravity, with small buffer. */
127
156
  export declare const MAX_JUMP_OFFSET = 1.15;
128
- /** Camera yaw looks along -Z; character mesh faces +Z at body rotation.y = 0. */
157
+ /** Camera yaw looks along -Z; character mesh faces +Z at body rotation.y = 0.
158
+ * @internal
159
+ */
129
160
  export declare function cameraYawToAvatarBodyYaw(cameraYaw: number): number;
@@ -10,6 +10,7 @@
10
10
  * touch controls) and its camera rigs (pointer lock, the per-frame look
11
11
  * channel).
12
12
  */
13
+ /** @internal */
13
14
  export function createEmptyMovementKeys() {
14
15
  return { w: false, a: false, s: false, d: false, shift: false, control: false, c: false, space: false };
15
16
  }
@@ -25,7 +26,8 @@ const IDLE_INTENT = {
25
26
  * Translate the set of held keys into an intent. When `canMove` is false (a
26
27
  * menu is open, the world is paused) the avatar is fully idle so it never
27
28
  * drifts behind an overlay.
28
- */
29
+ * @internal
30
+ */
29
31
  export function resolveMovementIntent(keys, canMove) {
30
32
  if (!canMove)
31
33
  return IDLE_INTENT;
@@ -52,6 +54,8 @@ export const MOVEMENT_TUNING = {
52
54
  walkSpeedMultiplier: 1.75,
53
55
  runSpeedMultiplier: 2.25,
54
56
  crouchSpeedMultiplier: 0.45,
57
+ /** Backward (S) travels this fraction of walk speed so retreating reads slower than advancing. */
58
+ backpedalSpeedMultiplier: 0.65,
55
59
  groundAcceleration: 26,
56
60
  airAcceleration: 12,
57
61
  groundFriction: 18,
@@ -70,15 +74,24 @@ export const MOVEMENT_TUNING = {
70
74
  /** Largest physics step we integrate so a stalled tab can't teleport the player. */
71
75
  maxFrameSeconds: 0.05,
72
76
  };
73
- /** Speed (units/s) the avatar should target given the active intent. */
74
- function resolveTargetSpeed(intent, baseSpeed) {
77
+ /**
78
+ * Speed (units/s) the avatar should target given the active intent. Crouch and run
79
+ * take precedence over backpedal; a plain backward intent (`forward < 0`) slows to
80
+ * {@link MOVEMENT_TUNING.backpedalSpeedMultiplier} (overridable via `tuning`), while a
81
+ * pure strafe keeps full speed.
82
+ */
83
+ function resolveTargetSpeed(intent, baseSpeed, tuning) {
84
+ const backpedal = tuning?.backpedalSpeedMultiplier ?? MOVEMENT_TUNING.backpedalSpeedMultiplier;
75
85
  const speedMultiplier = intent.crouching
76
86
  ? MOVEMENT_TUNING.crouchSpeedMultiplier
77
87
  : intent.running
78
88
  ? MOVEMENT_TUNING.runSpeedMultiplier
79
- : 1;
89
+ : intent.forward < 0
90
+ ? backpedal
91
+ : 1;
80
92
  return baseSpeed * MOVEMENT_TUNING.walkSpeedMultiplier * speedMultiplier;
81
93
  }
94
+ /** @internal */
82
95
  export function createPlayerMotionState() {
83
96
  return {
84
97
  horizontalVelocityX: 0,
@@ -98,10 +111,11 @@ export function createPlayerMotionState() {
98
111
  * (need not be normalized); the avatar's right axis is derived from it. Pulling
99
112
  * this out of the render loop is what lets us assert "held forward for N frames
100
113
  * crosses the room" in a unit test instead of only in the live game.
101
- */
102
- export function advancePlayerMotion(motion, intent, forwardX, forwardZ, baseSpeed, rawDeltaSeconds, tuning) {
114
+ * @internal
115
+ */
116
+ export function advancePlayerMotion(motion, intent, forwardX, forwardZ, baseSpeed, rawDeltaSeconds, tuning, options) {
103
117
  const deltaSeconds = Math.min(rawDeltaSeconds, MOVEMENT_TUNING.maxFrameSeconds);
104
- const targetSpeed = resolveTargetSpeed(intent, baseSpeed);
118
+ const targetSpeed = resolveTargetSpeed(intent, baseSpeed, tuning) * (options?.speedScale ?? 1);
105
119
  const gravityAcceleration = tuning?.gravityAcceleration ?? MOVEMENT_TUNING.gravityAcceleration;
106
120
  const jumpVelocity = tuning?.jumpVelocity ?? MOVEMENT_TUNING.jumpVelocity;
107
121
  let targetVelocityX = 0;
@@ -146,13 +160,19 @@ export function advancePlayerMotion(motion, intent, forwardX, forwardZ, baseSpee
146
160
  motion.horizontalVelocityX *= friction;
147
161
  motion.horizontalVelocityZ *= friction;
148
162
  }
163
+ const floating = options?.floating === true;
149
164
  const jumpPressed = intent.jumping;
150
- if (jumpPressed && !motion.jumpHeld && motion.grounded && !intent.crouching) {
165
+ if (jumpPressed && !motion.jumpHeld && motion.grounded && !intent.crouching && !floating) {
151
166
  motion.verticalVelocity = jumpVelocity;
152
167
  motion.grounded = false;
153
168
  }
154
169
  motion.jumpHeld = jumpPressed;
155
- if (!motion.grounded || motion.verticalVelocity > 0) {
170
+ if (floating) {
171
+ motion.verticalVelocity = 0;
172
+ motion.jumpOffset = 0;
173
+ motion.grounded = true;
174
+ }
175
+ else if (!motion.grounded || motion.verticalVelocity > 0) {
156
176
  motion.verticalVelocity -= gravityAcceleration * deltaSeconds;
157
177
  motion.jumpOffset += motion.verticalVelocity * deltaSeconds;
158
178
  if (motion.jumpOffset <= 0) {
@@ -188,7 +208,8 @@ function clampAxisStep(originalCoord, step, min, max) {
188
208
  * by `playerRadius`; an obstacle whose vertical span misses the player's
189
209
  * feet-to-head span is skipped entirely. Callers should pre-filter to nearby
190
210
  * objects — this also early-exits per obstacle on horizontal distance.
191
- */
211
+ * @internal
212
+ */
192
213
  export function resolveObstacleStep(current, stepX, stepZ, obstacles, playerRadius = DEFAULT_OBSTACLE_PLAYER_RADIUS) {
193
214
  const feetY = current[1];
194
215
  const headY = feetY + OBSTACLE_PLAYER_HEIGHT;
@@ -227,7 +248,24 @@ export function resolveObstacleStep(current, stepX, stepZ, obstacles, playerRadi
227
248
  }
228
249
  return { stepX: resultX, stepZ: resultZ };
229
250
  }
230
- /** Zeroes the off-axis component so travel is locked to a single world axis (`PlayerMovementConfig.mode: "axis"`). */
251
+ const OBSTACLE_GATHER_RADIUS = 3;
252
+ /** Placed objects within `radius` (XZ) of `center`, as {@link CollisionObstacle}s to pre-filter for {@link resolveObstacleStep}.
253
+ * @internal
254
+ */
255
+ export function nearbyObstacles(objects, center, radius = OBSTACLE_GATHER_RADIUS) {
256
+ const radiusSq = radius * radius;
257
+ const result = [];
258
+ for (const object of objects) {
259
+ const dx = object.position[0] - center[0];
260
+ const dz = object.position[2] - center[2];
261
+ if (dx * dx + dz * dz <= radiusSq)
262
+ result.push({ position: object.position });
263
+ }
264
+ return result;
265
+ }
266
+ /** Zeroes the off-axis component so travel is locked to a single world axis (`PlayerMovementConfig.mode: "axis"`).
267
+ * @internal
268
+ */
231
269
  export function constrainStepToAxis(stepX, stepZ, axis) {
232
270
  return axis === "x" ? { stepX, stepZ: 0 } : { stepX: 0, stepZ };
233
271
  }
@@ -235,13 +273,16 @@ export function constrainStepToAxis(stepX, stepZ, axis) {
235
273
  * Snap a world position to its containing cell's center, matching the
236
274
  * bounds-free form of `navGrid`'s and `tacticalGrid`'s `floor` + half-cell
237
275
  * convention (`PlayerMovementConfig.mode: "grid"`).
238
- */
276
+ * @internal
277
+ */
239
278
  export function snapPositionToGrid(x, z, cellSize) {
240
279
  return [(Math.floor(x / cellSize) + 0.5) * cellSize, (Math.floor(z / cellSize) + 0.5) * cellSize];
241
280
  }
242
281
  /** Peak jump height from MOVEMENT_TUNING.jumpVelocity + gravity, with small buffer. */
243
282
  export const MAX_JUMP_OFFSET = 1.15;
244
- /** Camera yaw looks along -Z; character mesh faces +Z at body rotation.y = 0. */
283
+ /** Camera yaw looks along -Z; character mesh faces +Z at body rotation.y = 0.
284
+ * @internal
285
+ */
245
286
  export function cameraYawToAvatarBodyYaw(cameraYaw) {
246
287
  return cameraYaw + Math.PI;
247
288
  }
@@ -0,0 +1,41 @@
1
+ import type { PhysicsConfig } from "../game/defineGame.js";
2
+ import type { PlayerMovementConfig, VoxelCollisionConfig } from "../game/playableGame.js";
3
+ import type { GameContext } from "../runtime/gameContext.js";
4
+ import type { InputFrame } from "../runtime/inputSnapshot.js";
5
+ import { type TerrainField } from "../world/terrain.js";
6
+ import type { WorldFeature } from "../world/features.js";
7
+ import { type MovementTuningOverrides } from "./movementModel.js";
8
+ /** The resolved, per-world movement configuration {@link stepPlayerMovement} integrates against — the same inputs the shell FrameDriver used to read piecemeal, gathered into one struct so single-player and host movement run identical math. */
9
+ export interface PlayerMovementTuning {
10
+ collision?: VoxelCollisionConfig;
11
+ movement?: PlayerMovementConfig;
12
+ physics?: MovementTuningOverrides;
13
+ ground: TerrainField;
14
+ hasTerrain: boolean;
15
+ }
16
+ /**
17
+ * Maps a game's declared `physics` onto the movement controllers' tuning. `PhysicsConfig.gravity` is a signed
18
+ * world acceleration (negative points down), but the controllers integrate `velocityY -= gravityAcceleration * dt`
19
+ * and expect a positive downward magnitude — so gravity is negated here to keep down-pointing gravity pulling down.
20
+ */
21
+ export declare function resolvePhysicsTuning(physics: PhysicsConfig | undefined): MovementTuningOverrides | undefined;
22
+ /** Gather a game's collision/movement/physics/world config into a {@link PlayerMovementTuning} — call once per world; both the shell and a host pass the result to {@link stepPlayerMovement}. */
23
+ export declare function resolvePlayerMovementTuning(opts: {
24
+ collision?: VoxelCollisionConfig;
25
+ movement?: PlayerMovementConfig;
26
+ physics?: PhysicsConfig;
27
+ world?: WorldFeature;
28
+ }): PlayerMovementTuning;
29
+ /** One player's current heading (radians), integrated by {@link stepPlayerMovement} — the shell reads it back into its camera/aim yaw. */
30
+ export declare function playerMovementHeading(ctx: GameContext, userId: string): number;
31
+ /** Drop a player's retained movement state (heading + kinematic body) — call on leave so a rejoin starts fresh instead of resuming stale velocity. */
32
+ export declare function forgetPlayerMovement(ctx: GameContext, userId: string): void;
33
+ /**
34
+ * Integrate one player's movement for a tick from their held-input frame and commit the pose — the single
35
+ * genre-agnostic controller both the shell (its local player) and a host (each connected player in `onTick`) call,
36
+ * so single-player and server-authoritative movement are identical. Reads the player's controlled entity, terrain,
37
+ * scene solids, and pending motion impulses; writes the entity pose via `setPose`. Retains heading + kinematic body
38
+ * per `userId` on the `ctx`. Pass `heading` to override the internally-integrated yaw (the shell owns yaw for its
39
+ * camera); omit it and the controller turns from the frame's `turnLeft`/`turnRight` actions.
40
+ */
41
+ export declare function stepPlayerMovement(ctx: GameContext, userId: string, input: InputFrame, dt: number, tuning: PlayerMovementTuning, heading?: number): void;