@v12-engine/engine 0.0.0-stage → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (341) hide show
  1. package/LICENSE +21 -0
  2. package/dist/abilities/buffs.d.ts +83 -0
  3. package/dist/abilities/castTold.d.ts +12 -0
  4. package/dist/abilities/charges.d.ts +28 -0
  5. package/dist/abilities/dispel.d.ts +9 -0
  6. package/dist/abilities/effectFields.d.ts +10 -0
  7. package/dist/abilities/effects/buff.d.ts +8 -0
  8. package/dist/abilities/effects/core.d.ts +1 -0
  9. package/dist/abilities/effects/damage.d.ts +1 -0
  10. package/dist/abilities/effects/heal.d.ts +2 -0
  11. package/dist/abilities/effects/missile.d.ts +1 -0
  12. package/dist/abilities/effects/moves.d.ts +11 -0
  13. package/dist/abilities/effects/passives.d.ts +15 -0
  14. package/dist/abilities/effects/sight.d.ts +4 -0
  15. package/dist/abilities/effects/spawn.d.ts +2 -0
  16. package/dist/abilities/effects/timed.d.ts +4 -0
  17. package/dist/abilities/effects/trade.d.ts +1 -0
  18. package/dist/abilities/effects.d.ts +122 -0
  19. package/dist/abilities/land.d.ts +21 -0
  20. package/dist/abilities/scaled.d.ts +21 -0
  21. package/dist/abilities/text.d.ts +113 -0
  22. package/dist/ai/area.d.ts +53 -0
  23. package/dist/ai/brain.d.ts +528 -0
  24. package/dist/ai/budget.d.ts +67 -0
  25. package/dist/ai/checks.d.ts +115 -0
  26. package/dist/ai/computer.d.ts +166 -0
  27. package/dist/ai/defence.d.ts +108 -0
  28. package/dist/ai/define.d.ts +21 -0
  29. package/dist/ai/economy.d.ts +129 -0
  30. package/dist/ai/geometry.d.ts +35 -0
  31. package/dist/ai/goals.d.ts +360 -0
  32. package/dist/ai/index.d.ts +38 -0
  33. package/dist/ai/knowledge.d.ts +418 -0
  34. package/dist/ai/lanes.d.ts +232 -0
  35. package/dist/ai/melee/build.d.ts +61 -0
  36. package/dist/ai/melee/goals.d.ts +299 -0
  37. package/dist/ai/melee/heroes.d.ts +27 -0
  38. package/dist/ai/melee/index.d.ts +14 -0
  39. package/dist/ai/melee/production.d.ts +8 -0
  40. package/dist/ai/melee/surrender.d.ts +24 -0
  41. package/dist/ai/micro.d.ts +278 -0
  42. package/dist/ai/mission.d.ts +195 -0
  43. package/dist/ai/missionRules.d.ts +18 -0
  44. package/dist/ai/module.d.ts +116 -0
  45. package/dist/ai/options.d.ts +61 -0
  46. package/dist/ai/plans/build.d.ts +280 -0
  47. package/dist/ai/plans/placement.d.ts +82 -0
  48. package/dist/ai/plans/plans.d.ts +105 -0
  49. package/dist/ai/plans/production.d.ts +210 -0
  50. package/dist/ai/plans/purse.d.ts +73 -0
  51. package/dist/ai/plans/tech.d.ts +37 -0
  52. package/dist/ai/profiles.d.ts +204 -0
  53. package/dist/ai/reach.d.ts +4 -0
  54. package/dist/ai/report.d.ts +203 -0
  55. package/dist/ai/roles.d.ts +133 -0
  56. package/dist/ai/rules.d.ts +288 -0
  57. package/dist/ai/scouting.d.ts +98 -0
  58. package/dist/ai/settings.d.ts +73 -0
  59. package/dist/ai/squads.d.ts +429 -0
  60. package/dist/ai/strength.d.ts +167 -0
  61. package/dist/ai/task.d.ts +118 -0
  62. package/dist/ai/tasks/attack.d.ts +7 -0
  63. package/dist/ai/tasks/capture.d.ts +21 -0
  64. package/dist/ai/tasks/creep.d.ts +16 -0
  65. package/dist/ai/tasks/defend.d.ts +29 -0
  66. package/dist/ai/tasks/drop.d.ts +34 -0
  67. package/dist/ai/tasks/escort.d.ts +16 -0
  68. package/dist/ai/tasks/gather.d.ts +23 -0
  69. package/dist/ai/tasks/harass.d.ts +7 -0
  70. package/dist/ai/tasks/hold.d.ts +20 -0
  71. package/dist/ai/tasks/index.d.ts +32 -0
  72. package/dist/ai/tasks/move.d.ts +19 -0
  73. package/dist/ai/tasks/patrol.d.ts +8 -0
  74. package/dist/ai/tasks/retreat.d.ts +20 -0
  75. package/dist/ai/tasks/scout.d.ts +29 -0
  76. package/dist/ai/tasks/shared.d.ts +74 -0
  77. package/dist/ai/team.d.ts +155 -0
  78. package/dist/ai/threat.d.ts +91 -0
  79. package/dist/ai/view.d.ts +366 -0
  80. package/dist/ai/waves.d.ts +126 -0
  81. package/dist/ai.js +6239 -0
  82. package/dist/ai.js.map +1 -0
  83. package/dist/aiTesting.d.ts +179 -0
  84. package/dist/areas.d.ts +149 -0
  85. package/dist/attacks.d.ts +66 -0
  86. package/dist/attributes.d.ts +66 -0
  87. package/dist/brain-BvVdUhX8.js +7659 -0
  88. package/dist/brain-BvVdUhX8.js.map +1 -0
  89. package/dist/builds-C6LfgvEU.js +460 -0
  90. package/dist/builds-C6LfgvEU.js.map +1 -0
  91. package/dist/bytes.d.ts +6 -0
  92. package/dist/camps.d.ts +95 -0
  93. package/dist/capture.d.ts +131 -0
  94. package/dist/cellLayers.d.ts +75 -0
  95. package/dist/cinematics.d.ts +194 -0
  96. package/dist/clock.d.ts +32 -0
  97. package/dist/commands.d.ts +235 -0
  98. package/dist/components.d.ts +184 -0
  99. package/dist/computers.d.ts +108 -0
  100. package/dist/concealment.d.ts +61 -0
  101. package/dist/coreComponents-syuh2fPG.js +5149 -0
  102. package/dist/coreComponents-syuh2fPG.js.map +1 -0
  103. package/dist/coreComponents.d.ts +1 -0
  104. package/dist/dashing.d.ts +8 -0
  105. package/dist/debug.d.ts +36 -0
  106. package/dist/debug.js +3 -0
  107. package/dist/debugCommands-CzjrSm66.js +14739 -0
  108. package/dist/debugCommands-CzjrSm66.js.map +1 -0
  109. package/dist/debugCommands.d.ts +213 -0
  110. package/dist/debugging.d.ts +10 -0
  111. package/dist/definitions.d.ts +43 -0
  112. package/dist/defs.d.ts +1162 -0
  113. package/dist/denying.d.ts +81 -0
  114. package/dist/destructibles.d.ts +27 -0
  115. package/dist/determinism-BCymQwiE.js +518 -0
  116. package/dist/determinism-BCymQwiE.js.map +1 -0
  117. package/dist/determinism.d.ts +121 -0
  118. package/dist/dialog.d.ts +94 -0
  119. package/dist/effectRefs.d.ts +16 -0
  120. package/dist/effects.d.ts +80 -0
  121. package/dist/endings.d.ts +22 -0
  122. package/dist/engagement.d.ts +108 -0
  123. package/dist/engineEvents.d.ts +710 -0
  124. package/dist/entity.d.ts +409 -0
  125. package/dist/entityIndex.d.ts +50 -0
  126. package/dist/errors.d.ts +85 -0
  127. package/dist/events.d.ts +97 -0
  128. package/dist/exactMath.d.ts +63 -0
  129. package/dist/features.d.ts +10 -0
  130. package/dist/fields.d.ts +114 -0
  131. package/dist/fixture.d.ts +17 -0
  132. package/dist/fog.d.ts +110 -0
  133. package/dist/formation.d.ts +111 -0
  134. package/dist/friendlyFire.d.ts +26 -0
  135. package/dist/game-DiJEN-Ks.js +5800 -0
  136. package/dist/game-DiJEN-Ks.js.map +1 -0
  137. package/dist/game.d.ts +501 -0
  138. package/dist/gameData.d.ts +325 -0
  139. package/dist/gameFiles.d.ts +26 -0
  140. package/dist/gates.d.ts +28 -0
  141. package/dist/generate.d.ts +403 -0
  142. package/dist/generateWorker.d.ts +39 -0
  143. package/dist/grid.d.ts +53 -0
  144. package/dist/ground.d.ts +127 -0
  145. package/dist/groundSpeed.d.ts +22 -0
  146. package/dist/hero.d.ts +177 -0
  147. package/dist/home.d.ts +14 -0
  148. package/dist/hooks.d.ts +780 -0
  149. package/dist/hotReload.d.ts +76 -0
  150. package/dist/ids.d.ts +26 -0
  151. package/dist/index.d.ts +227 -0
  152. package/dist/index.js +4701 -0
  153. package/dist/index.js.map +1 -0
  154. package/dist/inspect-D9dWHmZ0.js +491 -0
  155. package/dist/inspect-D9dWHmZ0.js.map +1 -0
  156. package/dist/inspect.d.ts +176 -0
  157. package/dist/inventory.d.ts +18 -0
  158. package/dist/items.d.ts +91 -0
  159. package/dist/lanes.d.ts +213 -0
  160. package/dist/life.d.ts +53 -0
  161. package/dist/local-Dkovq42k.js +1379 -0
  162. package/dist/local-Dkovq42k.js.map +1 -0
  163. package/dist/log.d.ts +140 -0
  164. package/dist/manaBurn.d.ts +39 -0
  165. package/dist/map/file.d.ts +114 -0
  166. package/dist/map/images.d.ts +18 -0
  167. package/dist/map/look.d.ts +47 -0
  168. package/dist/map/pathProfile.d.ts +13 -0
  169. package/dist/map/resize.d.ts +54 -0
  170. package/dist/map/schema.d.ts +10 -0
  171. package/dist/map/terrain.d.ts +32 -0
  172. package/dist/map/types.d.ts +613 -0
  173. package/dist/map.d.ts +7 -0
  174. package/dist/mapCheck/cells.d.ts +19 -0
  175. package/dist/mapCheck/rule.d.ts +30 -0
  176. package/dist/mapCheck/rules/names.d.ts +3 -0
  177. package/dist/mapCheck/rules/objects.d.ts +3 -0
  178. package/dist/mapCheck/rules/paths.d.ts +3 -0
  179. package/dist/mapCheck/rules/players.d.ts +3 -0
  180. package/dist/mapCheck/rules/races.d.ts +3 -0
  181. package/dist/mapCheck/rules/random.d.ts +3 -0
  182. package/dist/mapCheck/rules/regions.d.ts +3 -0
  183. package/dist/mapCheck/rules/targets.d.ts +3 -0
  184. package/dist/mapCheck/rules/walking.d.ts +3 -0
  185. package/dist/mapCheck.d.ts +23 -0
  186. package/dist/mapFields.d.ts +364 -0
  187. package/dist/mapFile.d.ts +23 -0
  188. package/dist/mapMeasure.d.ts +95 -0
  189. package/dist/mapMerge.d.ts +19 -0
  190. package/dist/mapObjectives.d.ts +82 -0
  191. package/dist/mapObjects.d.ts +1 -0
  192. package/dist/math.d.ts +44 -0
  193. package/dist/messages.d.ts +150 -0
  194. package/dist/missionRules-C-bGxm0Q.js +523 -0
  195. package/dist/missionRules-C-bGxm0Q.js.map +1 -0
  196. package/dist/missionRules.d.ts +179 -0
  197. package/dist/mods.d.ts +146 -0
  198. package/dist/names.d.ts +93 -0
  199. package/dist/navigation/agentParams.d.ts +4 -0
  200. package/dist/navigation/air.d.ts +89 -0
  201. package/dist/navigation/builds.d.ts +140 -0
  202. package/dist/navigation/groundAreas.d.ts +23 -0
  203. package/dist/navigation/navigation.d.ts +127 -0
  204. package/dist/navigation/recast.d.ts +214 -0
  205. package/dist/navigation/sidePaths.d.ts +69 -0
  206. package/dist/navigation/sized.d.ts +1 -0
  207. package/dist/navigation-worker.js +11 -0
  208. package/dist/navigation-worker.js.map +1 -0
  209. package/dist/nearest.d.ts +8 -0
  210. package/dist/noise.d.ts +12 -0
  211. package/dist/objectives.d.ts +93 -0
  212. package/dist/orders/basic.d.ts +96 -0
  213. package/dist/orders/build.d.ts +91 -0
  214. package/dist/orders/cast.d.ts +105 -0
  215. package/dist/orders/facts.d.ts +14 -0
  216. package/dist/orders/harvest.d.ts +94 -0
  217. package/dist/orders/idle.d.ts +7 -0
  218. package/dist/orders/items.d.ts +14 -0
  219. package/dist/orders/queue.d.ts +24 -0
  220. package/dist/pack.schema.json +6621 -0
  221. package/dist/packs/director/index.d.ts +81 -0
  222. package/dist/packs/heroes/campaign.d.ts +137 -0
  223. package/dist/packs/heroes/carry.d.ts +59 -0
  224. package/dist/packs/heroes/commands.d.ts +6 -0
  225. package/dist/packs/heroes/hire.d.ts +9 -0
  226. package/dist/packs/heroes/index.d.ts +12 -0
  227. package/dist/packs/heroes/making.d.ts +16 -0
  228. package/dist/packs/heroes/respawn.d.ts +42 -0
  229. package/dist/packs/moba/index.d.ts +34 -0
  230. package/dist/packs/pack.d.ts +84 -0
  231. package/dist/packs-g5thvmGn.js +3199 -0
  232. package/dist/packs-g5thvmGn.js.map +1 -0
  233. package/dist/packs.d.ts +84 -0
  234. package/dist/paths.d.ts +51 -0
  235. package/dist/plain.d.ts +17 -0
  236. package/dist/player.d.ts +117 -0
  237. package/dist/portals.d.ts +66 -0
  238. package/dist/prefabs.d.ts +139 -0
  239. package/dist/presetBuildings.d.ts +52 -0
  240. package/dist/presetGround.d.ts +22 -0
  241. package/dist/profiles-B3NS9jwk.js +335 -0
  242. package/dist/profiles-B3NS9jwk.js.map +1 -0
  243. package/dist/races.d.ts +136 -0
  244. package/dist/randomGroups.d.ts +2 -0
  245. package/dist/registry.d.ts +464 -0
  246. package/dist/remains.d.ts +119 -0
  247. package/dist/replication.d.ts +103 -0
  248. package/dist/rng.d.ts +17 -0
  249. package/dist/rules.d.ts +395 -0
  250. package/dist/rulesCheck.d.ts +37 -0
  251. package/dist/runes.d.ts +41 -0
  252. package/dist/save.d.ts +277 -0
  253. package/dist/scenario.d.ts +56 -0
  254. package/dist/scheduler.d.ts +67 -0
  255. package/dist/score.d.ts +306 -0
  256. package/dist/sequences.d.ts +132 -0
  257. package/dist/server/doorman.d.ts +21 -0
  258. package/dist/server/gameServer.d.ts +346 -0
  259. package/dist/server/index.d.ts +24 -0
  260. package/dist/server/lobby.d.ts +1 -0
  261. package/dist/server/log.d.ts +13 -0
  262. package/dist/server/match.d.ts +24 -0
  263. package/dist/server/mode.d.ts +168 -0
  264. package/dist/server/navigation-worker.d.ts +1 -0
  265. package/dist/server/navigation.d.ts +11 -0
  266. package/dist/server/ops.d.ts +78 -0
  267. package/dist/server/packs.d.ts +15 -0
  268. package/dist/server/ratings.d.ts +62 -0
  269. package/dist/server/relay.d.ts +34 -0
  270. package/dist/server/rooms.d.ts +162 -0
  271. package/dist/server/seat.d.ts +2 -0
  272. package/dist/server/seatSettings.d.ts +15 -0
  273. package/dist/server/secret.d.ts +5 -0
  274. package/dist/server/start.d.ts +54 -0
  275. package/dist/server/websocket.d.ts +74 -0
  276. package/dist/server.js +2861 -0
  277. package/dist/server.js.map +1 -0
  278. package/dist/session/can.d.ts +20 -0
  279. package/dist/session/commandReplay.d.ts +92 -0
  280. package/dist/session/debug.d.ts +65 -0
  281. package/dist/session/delay.d.ts +15 -0
  282. package/dist/session/delta.d.ts +98 -0
  283. package/dist/session/entityState.d.ts +1 -0
  284. package/dist/session/local.d.ts +214 -0
  285. package/dist/session/memory.d.ts +27 -0
  286. package/dist/session/protocol.d.ts +1155 -0
  287. package/dist/session/remote.d.ts +530 -0
  288. package/dist/session/replay.d.ts +114 -0
  289. package/dist/session/seed.d.ts +7 -0
  290. package/dist/session/share.d.ts +78 -0
  291. package/dist/session/socket.d.ts +8 -0
  292. package/dist/session/wire.d.ts +153 -0
  293. package/dist/session/worker.d.ts +227 -0
  294. package/dist/shared.d.ts +171 -0
  295. package/dist/sides.d.ts +75 -0
  296. package/dist/sight.d.ts +27 -0
  297. package/dist/simulate-oXBiw1Ff.js +167 -0
  298. package/dist/simulate-oXBiw1Ff.js.map +1 -0
  299. package/dist/simulate-worker.d.ts +1 -0
  300. package/dist/simulate-worker.js +28 -0
  301. package/dist/simulate-worker.js.map +1 -0
  302. package/dist/simulate.d.ts +154 -0
  303. package/dist/smart.d.ts +9 -0
  304. package/dist/spatial.d.ts +62 -0
  305. package/dist/spawning.d.ts +33 -0
  306. package/dist/stances.d.ts +76 -0
  307. package/dist/start.d.ts +71 -0
  308. package/dist/stats.d.ts +122 -0
  309. package/dist/summons.d.ts +63 -0
  310. package/dist/systems/abilities.d.ts +3 -0
  311. package/dist/systems/combat.d.ts +71 -0
  312. package/dist/systems/combatTold.d.ts +14 -0
  313. package/dist/systems/construction.d.ts +34 -0
  314. package/dist/systems/economy.d.ts +21 -0
  315. package/dist/systems/fog.d.ts +19 -0
  316. package/dist/systems/life.d.ts +3 -0
  317. package/dist/systems/movement.d.ts +105 -0
  318. package/dist/systems/orders.d.ts +7 -0
  319. package/dist/systems/production.d.ts +49 -0
  320. package/dist/systems/productionQueue.d.ts +40 -0
  321. package/dist/systems/victory.d.ts +14 -0
  322. package/dist/talk.d.ts +65 -0
  323. package/dist/tech.d.ts +62 -0
  324. package/dist/techTree.d.ts +38 -0
  325. package/dist/terrain.d.ts +173 -0
  326. package/dist/terrainSave.d.ts +29 -0
  327. package/dist/testing.d.ts +58 -0
  328. package/dist/testing.js +822 -0
  329. package/dist/testing.js.map +1 -0
  330. package/dist/tiles.d.ts +34 -0
  331. package/dist/timers.d.ts +146 -0
  332. package/dist/tomes.d.ts +48 -0
  333. package/dist/trade.d.ts +28 -0
  334. package/dist/transport.d.ts +76 -0
  335. package/dist/tunables.d.ts +45 -0
  336. package/dist/upkeep.d.ts +16 -0
  337. package/dist/veterancy.d.ts +80 -0
  338. package/dist/walls.d.ts +86 -0
  339. package/dist/world.d.ts +1118 -0
  340. package/package.json +80 -5
  341. package/README.md +0 -3
@@ -0,0 +1,78 @@
1
+ import type { PlayerId } from '#engine/entity';
2
+ import type { World } from '#engine/world';
3
+ /**
4
+ * What the relay tells pages besides the game itself
5
+ *
6
+ * @beta
7
+ */
8
+ export type RelayNotice =
9
+ /** To a sharing page: it shares under `key` now */
10
+ {
11
+ type: 'shared';
12
+ key: string;
13
+ }
14
+ /** To a sharing page: another page shares under that key already */
15
+ | {
16
+ type: 'taken';
17
+ key: string;
18
+ }
19
+ /** To a sharing page: someone watches, by the id the relay gave them */
20
+ | {
21
+ type: 'watcher';
22
+ id: number;
23
+ }
24
+ /** To a sharing page: what a watcher said (that it got a tick, a ping) */
25
+ | {
26
+ type: 'from';
27
+ watcher: number;
28
+ text: string;
29
+ }
30
+ /** To a sharing page: a watcher left */
31
+ | {
32
+ type: 'gone';
33
+ watcher: number;
34
+ }
35
+ /** To a watcher: nothing is shared under the key right now. The game comes once it is */
36
+ | {
37
+ type: 'waiting';
38
+ key: string;
39
+ }
40
+ /** To a watcher: the game shared ended. The next one under the key comes when it is shared */
41
+ | {
42
+ type: 'ended';
43
+ key: string;
44
+ };
45
+ /** @beta */
46
+ export interface ShareOptions {
47
+ /** The relay's address, `ws://host:port` */
48
+ url: string;
49
+ /** What watchers ask for: the same for every game of a campaign, so they stay from one mission to the next */
50
+ key: string;
51
+ /** What it is, for the relay's log */
52
+ name: string;
53
+ /** Whose side watchers see it from: they get that player's lines and cinematics, and see everything besides */
54
+ player: PlayerId;
55
+ /** Snapshots a second to each watcher. 20 when left out */
56
+ sendRate?: number;
57
+ }
58
+ /**
59
+ * A game shared for watching (`shareGame`)
60
+ *
61
+ * @beta
62
+ */
63
+ export interface SharedGame {
64
+ /** `shared` once the relay has it; `taken` when another page shares under the key; `closed` once it is over */
65
+ readonly state: 'shared' | 'taken' | 'closed';
66
+ /** How many watch it now */
67
+ readonly watchers: number;
68
+ /** Told whenever the state or the number of watchers changes */
69
+ onChange(handler: () => void): void;
70
+ /** Stops sharing: the watchers are told it ended */
71
+ close(): void;
72
+ }
73
+ /**
74
+ * Shares the page's world through a relay, for others to watch. Fails when the relay cannot be reached
75
+ *
76
+ * @beta
77
+ */
78
+ export declare function shareGame(world: World, options: ShareOptions): Promise<SharedGame>;
@@ -0,0 +1,8 @@
1
+ import type { Transport } from './remote';
2
+ /**
3
+ * The player's end of a connection to a server, over a WebSocket: what `connect` and a server's lobby talk through.
4
+ * Resolves once the connection is open; fails when it cannot be made
5
+ *
6
+ * @beta
7
+ */
8
+ export declare function openSocket(url: string): Promise<Transport>;
@@ -0,0 +1,153 @@
1
+ /**
2
+ * What goes over the wire between a host and a player, both layers of it in one place (design review E11): the game's
3
+ * (`GameHostMessage`, `GameCommandMessage`: a `SessionHost` and a `RemoteSession`) and a server's lobby beside it
4
+ * (`LobbyServerMessage`, `LobbyPlayerMessage`: a `GameServer`). One union each way (`HostToPlayer`, `PlayerToHost`),
5
+ * discriminated by `type` (no type is both a game's and a lobby's), read with a shape check (`readHostMessage`,
6
+ * `readPlayerMessage`), and `PROTOCOL_VERSION` is of all of it
7
+ */
8
+ import type { GameData } from '#engine/gameData';
9
+ import type { Inspection, InspectTarget, LoggedEvent, WorldListing } from '#engine/inspect';
10
+ import type { PlayerId } from '#engine/entity';
11
+ import type { GameResult, ServerHooks, ServerSeat } from '#engine/game';
12
+ import type { SavedGround } from '#engine/ground';
13
+ import type { MapCamera, MapDoodad, MapEnvironment, MapPath, MapRegion } from '#engine/map';
14
+ import type { Delta } from './delta';
15
+ import type { RelayNotice } from './share';
16
+ /**
17
+ * What the host sends a player
18
+ *
19
+ * @beta
20
+ */
21
+ export type GameHostMessage = {
22
+ type: 'welcome';
23
+ /** The version of the wire the host speaks (`PROTOCOL_VERSION`): a player of another refuses the game */
24
+ protocol: number;
25
+ player: PlayerId;
26
+ tickRate: number;
27
+ /** The game module the world runs, by id, and the version of its data (`Registry.dataHash`): the player's has to be the same */
28
+ game: string;
29
+ hash: string;
30
+ /**
31
+ * The ground: all of it, or the map of the game it started as and what changed of it since (S36). A player
32
+ * without that map asks for it (`ground`), and is sent it in parts
33
+ */
34
+ terrain: SavedGround;
35
+ /** What the map looks like beyond its ground, for the screen */
36
+ environment?: MapEnvironment;
37
+ /** Its scenery, for the screen */
38
+ doodads?: MapDoodad[];
39
+ /** Its regions, for the screen: what mist in places lies over by name */
40
+ regions?: MapRegion[];
41
+ /** Its views saved under names */
42
+ cameras?: MapCamera[];
43
+ /** Its paths, for a cinematic's camera on a rail */
44
+ paths?: MapPath[];
45
+ /** What its definitions were changed to while it ran (`world.redefine`), copies and all: put in the player's registry */
46
+ redefinitions?: GameData;
47
+ /** Everything the player knows, as a delta without a base */
48
+ first: Delta;
49
+ /** The player only watches, and sees everything */
50
+ observer?: boolean;
51
+ /** The player may use the debug tools (`world.debugPlayers`): the host follows the world for them (`debug`) */
52
+ debug?: true;
53
+ } | {
54
+ type: 'pong';
55
+ at: number;
56
+ }
57
+ /** A part of the ground a world started as, for a player who does not have its map: `text` of `parts`, joined, is a `TerrainSave` */
58
+ | {
59
+ type: 'ground';
60
+ part: number;
61
+ parts: number;
62
+ text: string;
63
+ }
64
+ /** The game ended on an error in its rules (`World.failure`): what the players are told of it */
65
+ | {
66
+ type: 'failed';
67
+ message: string;
68
+ } | ({
69
+ type: 'delta';
70
+ } & Delta)
71
+ /** The debug tools' view of the world (`SessionDebug`), for a player who may use them and follows something: every tenth of a second */
72
+ | {
73
+ type: 'debug';
74
+ inspection: Inspection | null;
75
+ world: WorldListing | null;
76
+ log: readonly LoggedEvent[];
77
+ };
78
+ /**
79
+ * What the debug tools of a screen ask of a world elsewhere (`SessionDebug`), as said over the wire or to a worker
80
+ *
81
+ * @beta
82
+ */
83
+ export interface DebugAsk {
84
+ inspect?: InspectTarget | null;
85
+ set?: {
86
+ path: (string | number)[];
87
+ value: number | boolean;
88
+ };
89
+ listing?: boolean;
90
+ logging?: boolean;
91
+ clearLog?: true;
92
+ }
93
+ /**
94
+ * What the server tells everyone connected, as it changes
95
+ *
96
+ * @beta
97
+ */
98
+ export type LobbyServerMessage = {
99
+ type: 'lobby';
100
+ mode: string;
101
+ game: string;
102
+ phase: 'lobby' | 'game' | 'ended';
103
+ seats: ServerSeat[];
104
+ settings: Record<string, string>;
105
+ /** What the game offers to set (`ServerHooks.settings`) */
106
+ offered: NonNullable<ServerHooks['settings']>;
107
+ /** What the game offers to set for each seat (`ServerHooks.seatSettings`, and a race: `seatSettingsOf`) */
108
+ seatOffered: NonNullable<ServerHooks['seatSettings']>;
109
+ } | {
110
+ type: 'seated';
111
+ player: PlayerId;
112
+ token: string;
113
+ }
114
+ /** A line said in the lobby (`lobbyChat`): by whom, their seat where they have one */
115
+ | {
116
+ type: 'lobbyChat';
117
+ player?: PlayerId;
118
+ name: string;
119
+ text: string;
120
+ } | {
121
+ type: 'watching';
122
+ player: PlayerId;
123
+ } | {
124
+ type: 'full';
125
+ } | {
126
+ type: 'refused';
127
+ reason: string;
128
+ }
129
+ /** The game paused, or going on: by a player (`player`, for `seconds` at most) or by an admin (no player) */
130
+ | {
131
+ type: 'paused';
132
+ paused: boolean;
133
+ player?: PlayerId;
134
+ seconds?: number;
135
+ } | {
136
+ type: 'result';
137
+ result: GameResult;
138
+ };
139
+ /**
140
+ * What a player is told besides the game: a server's lobby, a pause, the result, or, watching through a relay, that
141
+ * nothing is shared yet or that the game watched ended
142
+ *
143
+ * @beta
144
+ */
145
+ export type ServerToPlayer = LobbyServerMessage | Extract<RelayNotice, {
146
+ type: 'waiting' | 'ended';
147
+ }>;
148
+ /**
149
+ * Everything a host, a server or a relay sends a player
150
+ *
151
+ * @beta
152
+ */
153
+ export type HostToPlayer = GameHostMessage | ServerToPlayer;
@@ -0,0 +1,227 @@
1
+ import type { PlayerId } from '#engine/entity';
2
+ import { type GameModule } from '#engine/game';
3
+ import { type LogEntry, Logger } from '#engine/log';
4
+ import type { GameMap } from '#engine/map';
5
+ import type { Message } from '#engine/messages';
6
+ import { type NavigationBuild } from '#engine/navigation/builds';
7
+ import { type WorldSave } from '#engine/save';
8
+ import type { World } from '#engine/world';
9
+ import type { SystemTiming } from '#engine/scheduler';
10
+ import type { SessionCan, SessionDebug } from './protocol';
11
+ import { type ConnectOptions, RemoteSession } from './remote';
12
+ /**
13
+ * What a worker is, as far as a game goes: a page's `Worker`, or Node's `worker_threads` one
14
+ *
15
+ * @beta
16
+ */
17
+ export interface WorldWorkerLike {
18
+ postMessage(message: unknown, transfer?: unknown[]): void;
19
+ addEventListener?(type: 'message' | 'error', listener: (event: {
20
+ data?: unknown;
21
+ message?: string;
22
+ }) => void): void;
23
+ removeEventListener?(type: 'message' | 'error', listener: (event: {
24
+ data?: unknown;
25
+ message?: string;
26
+ }) => void): void;
27
+ on?(type: 'message' | 'error', listener: (value: unknown) => void): void;
28
+ off?(type: 'message' | 'error', listener: (value: unknown) => void): void;
29
+ }
30
+ /**
31
+ * Where a worker hears and answers: a page's worker scope, or Node's `parentPort`
32
+ *
33
+ * @beta
34
+ */
35
+ export interface WorldPort {
36
+ postMessage(message: unknown, transfer?: unknown[]): void;
37
+ addEventListener?(type: 'message', listener: (event: {
38
+ data: unknown;
39
+ }) => void): void;
40
+ on?(type: 'message', listener: (value: unknown) => void): void;
41
+ }
42
+ /**
43
+ * What the page says a game in a worker is made from: plain data, which is all that crosses
44
+ *
45
+ * @beta
46
+ */
47
+ export interface WorkerGame {
48
+ /** A map of the game: the world is made from it. Or a save to go on from (`from`); or neither, where the worker makes its world in code */
49
+ map?: GameMap;
50
+ from?: WorldSave;
51
+ /** Who the player at the screen is: as the worker says (`ServeWorldOptions.player`), then the map's first with a start, when left out */
52
+ player?: PlayerId;
53
+ seed?: number;
54
+ /** Whether the player may use the debug tools, and sees everything from the start */
55
+ debug?: boolean;
56
+ reveal?: boolean;
57
+ /** Anything else the worker's own code is to know (`start`, `world`): plain data */
58
+ args?: unknown;
59
+ }
60
+ /**
61
+ * What the worker's file gives besides the game: its code that runs on the world, which cannot be sent
62
+ *
63
+ * @beta
64
+ */
65
+ export interface ServeWorldOptions {
66
+ /** A world made in code, where the page gives neither a map nor a save: generated ground, players of its own */
67
+ world?: (context: {
68
+ rules: GameModule;
69
+ seed: number;
70
+ args: unknown;
71
+ log: Logger;
72
+ }) => World | Promise<World>;
73
+ /** What the game does once a new world is made, before anyone plays: as `launch`'s `start`, which a worker's game has here */
74
+ start?: (world: World, context: {
75
+ player: PlayerId;
76
+ map?: GameMap;
77
+ args: unknown;
78
+ }) => void | Promise<void>;
79
+ /** Who the player at the screen is, where the page does not say */
80
+ player?: (world: World, map?: GameMap) => PlayerId;
81
+ /** Where it hears: the worker's own scope when left out (a page's worker); Node's `parentPort` in a worker thread */
82
+ port?: WorldPort;
83
+ /**
84
+ * A new version of the game, loaded again in the worker as the page asks (hot reload: the page's game took one, and
85
+ * a worker has no hot reload of its own). The game's module imported anew, so that the dev server gives it as it is
86
+ * now: `(version) => import(/* @vite-ignore *\/ `./index.ts?t=${version}`).then((module) => module.myGame)` (a path
87
+ * from the worker's file). Only ever asked for in the dev server. Without it, a game in the worker keeps the version it began with
88
+ */
89
+ reload?: (version: number) => Promise<GameModule | undefined> | GameModule | undefined;
90
+ }
91
+ /** What goes between the page and the worker besides the session's own text */
92
+ type ToWorker = ({
93
+ vg: 'start';
94
+ } & WorkerGame) | {
95
+ vg: 'stop';
96
+ } | {
97
+ vg: 'reload';
98
+ } | {
99
+ vg: 'speed';
100
+ speed: number;
101
+ } | {
102
+ vg: 'advance';
103
+ ticks: number;
104
+ } | {
105
+ vg: 'save';
106
+ id: number;
107
+ } | {
108
+ vg: 'navigation';
109
+ id: number;
110
+ build: NavigationBuild;
111
+ } | {
112
+ vg: 'profile';
113
+ on: boolean;
114
+ };
115
+ type FromWorker = {
116
+ vg: 'ready';
117
+ player: PlayerId;
118
+ } | {
119
+ vg: 'refused';
120
+ message: string;
121
+ stack?: string;
122
+ } | {
123
+ vg: 'saved';
124
+ id: number;
125
+ save?: WorldSave;
126
+ error?: string;
127
+ } | {
128
+ vg: 'built';
129
+ id: number;
130
+ data?: Uint8Array;
131
+ error?: string;
132
+ } | {
133
+ vg: 'checkpoint';
134
+ label: Message;
135
+ save: WorldSave;
136
+ } | {
137
+ vg: 'log';
138
+ entry: LogEntry;
139
+ } | {
140
+ vg: 'timing';
141
+ tick: number;
142
+ tickMax: number;
143
+ send: number;
144
+ systems: SystemTiming[];
145
+ };
146
+ /**
147
+ * What a game's worker file does: `serveWorld(game, { start })`. It waits for the page to say what to play (a map, a
148
+ * save, or nothing for a world made here in code), makes the world, runs it by the clock, and seats the page's player
149
+ * at it. A new game asked for ends the one before: a restart is the same worker, its navigation built already
150
+ *
151
+ * @beta
152
+ */
153
+ export declare function serveWorld(first: GameModule, options?: ServeWorldOptions): void;
154
+ /**
155
+ * A seat at a game run in a worker of this page (`workerSession`): a `RemoteSession` whose host is a message away,
156
+ * with what a game played in the page has besides: its pace held and stepped (`speed`, `advance`), a save of it
157
+ * (`save`), the checkpoint to start again from, what it says in its log, the debug tools' view, and where its time went
158
+ *
159
+ * @beta
160
+ */
161
+ export declare class WorkerSession extends RemoteSession {
162
+ /** What the world says (`World.log`), said again here: the page shows it with its own */
163
+ log: Logger;
164
+ checkpoint?: {
165
+ label: Message;
166
+ save: WorldSave;
167
+ };
168
+ /** The debug tools' view of the world, where they are on: over the session's own words, as a server's is */
169
+ get debug(): SessionDebug | undefined;
170
+ /** Its pace held and stepped, saves of it, the debug tools' view where they are on, and where its time went and in which systems */
171
+ readonly can: SessionCan;
172
+ private pace;
173
+ private timed?;
174
+ /** Milliseconds the page took to take in what the worker sent, each time, evened out: its share of a game run there */
175
+ received: number;
176
+ private postToWorker;
177
+ private readonly saves;
178
+ private nextSave;
179
+ private stopHearing;
180
+ /** What `workerSession` gives it once it is made: the way to the worker, and what stops hearing it */
181
+ wire(post: (message: ToWorker) => void, log: Logger, stop: () => void): void;
182
+ /** What the worker said that is not the session's own text */
183
+ heard(said: FromWorker): void;
184
+ /**
185
+ * How far behind the newest tick the screen is shown, in ticks: one, and room for how unevenly they come (a tick
186
+ * that took long comes late). Less than over a wire, where two are kept in hand: there is no line to stall here
187
+ */
188
+ get delay(): number;
189
+ get speed(): number;
190
+ set speed(speed: number);
191
+ advance(ticks?: number): void;
192
+ /**
193
+ * Asks the worker to take a new version of the game (hot reload): it loads the game again itself, as its file says
194
+ * (`serveWorld` `reload`), and puts it into its world
195
+ */
196
+ reloadGame(): void;
197
+ save(): Promise<WorldSave>;
198
+ timing(): {
199
+ tick: number;
200
+ tickMax: number;
201
+ send: number;
202
+ receive: number;
203
+ systems: SystemTiming[];
204
+ } | undefined;
205
+ /** Ends the game in the worker. The worker is the page's: it stays, for the next game, until the page ends it */
206
+ dispose(): void;
207
+ }
208
+ /**
209
+ * What a seat at a worker's game is asked for: what to play (`WorkerGame`), and what `connect` takes
210
+ *
211
+ * @beta
212
+ */
213
+ export interface WorkerSessionOptions extends WorkerGame, Pick<ConnectOptions, 'navigation' | 'maps'> {
214
+ game: GameModule;
215
+ /** The logger what the world says is said under, in the page: the root one when left out */
216
+ log?: Logger;
217
+ }
218
+ /**
219
+ * Plays a game in a worker, and seats this page's player at it: the worker's file calls `serveWorld` with the same
220
+ * game. Settles once the world is made there and its welcome is in; fails with what the worker said went wrong
221
+ *
222
+ * const session = await workerSession(new Worker(new URL('./game.worker.ts', import.meta.url), { type: 'module' }), { game, map })
223
+ *
224
+ * @beta
225
+ */
226
+ export declare function workerSession(worker: WorldWorkerLike, options: WorkerSessionOptions): Promise<WorkerSession>;
227
+ export {};
@@ -0,0 +1,171 @@
1
+ /**
2
+ * Rules the simulation and a player's screen both need, written once. Each works on plain facts that a world
3
+ * entity and a client's view of one can both give, so the screen greys out a button for the very reason the
4
+ * simulation would refuse it, and a game's own rules (items 9 to 11) reach both alike.
5
+ *
6
+ * The simulation has the last word all the same: the screen may know less than it does (a buff it is not told
7
+ * of, a step it has not seen yet), and only uses these to say something sooner.
8
+ */
9
+ import { type AbilityDef, type Cost, type EntityKind, type Layer, type UnitTypeDef } from './defs';
10
+ import { type Message } from './messages';
11
+ import { type Purse } from './player';
12
+ import type { Registry } from './registry';
13
+ /**
14
+ * Who a target is to the one using an ability on it
15
+ *
16
+ * @beta
17
+ */
18
+ export type Relation = 'self' | 'ally' | 'enemy' | 'neutral';
19
+ /**
20
+ * What there is to know about a target, for whether an ability may be used on it
21
+ *
22
+ * @beta
23
+ */
24
+ export interface TargetFacts {
25
+ kind: EntityKind;
26
+ layer: Layer;
27
+ hero: boolean;
28
+ invulnerable: boolean;
29
+ relation: Relation;
30
+ /** Immune to spells (see `UnitTypeDef.spellImmune`): no ability touches it but its own, and those that get through */
31
+ spellImmune?: boolean;
32
+ }
33
+ /**
34
+ * Why an ability may not be used on a target, or undefined when it may
35
+ *
36
+ * @beta
37
+ */
38
+ export declare function targetRefusal(ability: AbilityDef, target: TargetFacts): Message | undefined;
39
+ /**
40
+ * How far away the target of an ability may be: what it says, and for some as far as the caster's attacks reach on top
41
+ *
42
+ * @beta
43
+ */
44
+ export declare const abilityReach: (ability: AbilityDef, level: number, attackRange: number) => number;
45
+ /**
46
+ * What there is to know about an ability and its user, for whether it can be used right now
47
+ *
48
+ * @beta
49
+ */
50
+ export interface ReadyFacts {
51
+ /** 0 for one not learned yet */
52
+ level: number;
53
+ /** Seconds until it can be used again */
54
+ cooldown: number;
55
+ /** Uses left, of an ability with charges (`chargesLeft`): none, and it is not ready */
56
+ charges?: number;
57
+ mana: number;
58
+ hp: number;
59
+ maxHp: number;
60
+ /** It comes from something carried: items ask for no mana, and silence does not stop them */
61
+ item?: boolean;
62
+ /** One of the spells the hero brought along rather than learned: silence does not stop those either */
63
+ spell?: boolean;
64
+ silenced?: boolean;
65
+ /** The debug switch that makes abilities cost nothing */
66
+ noManaCosts?: boolean;
67
+ /** What the simulation's `canCast` hook decided instead, when it told the screen: a reason, or null for none */
68
+ decided?: Message | null;
69
+ }
70
+ /**
71
+ * How many uses an ability with charges has left (`AbilityDef.charges`), at its level: what its state says, or all it
72
+ * holds when that says nothing. Undefined for an ability without charges
73
+ *
74
+ * @beta
75
+ */
76
+ export declare function chargesLeft(ability: AbilityDef, state: {
77
+ level: number;
78
+ charges?: number;
79
+ }): number | undefined;
80
+ /**
81
+ * Why an ability cannot be used right now, or undefined when it can
82
+ *
83
+ * @beta
84
+ */
85
+ export declare function abilityRefusal(ability: AbilityDef, facts: ReadyFacts): Message | undefined;
86
+ /**
87
+ * What there is to know about a player, for whether they can make something
88
+ *
89
+ * @beta
90
+ */
91
+ export interface PlayerFacts {
92
+ resources: Readonly<Purse>;
93
+ supplyUsed: number;
94
+ supplyCap: number;
95
+ /** The game's other pools of supply, by name (`GameRules.supply.pools`): left out in a game with none */
96
+ supplies?: Readonly<Record<string, {
97
+ used: number;
98
+ cap: number;
99
+ }>>;
100
+ /** Unit types they have, finished, which is what requirements ask for */
101
+ tech: ReadonlySet<string> | readonly string[];
102
+ /** Types of the heroes they have, fallen ones and ones being made included */
103
+ heroes: readonly string[];
104
+ /**
105
+ * What the simulation's `requirement` hook decided, where it differs from what the requirements say: by unit or
106
+ * structure type, and `upgrade:<id>` for the next level of research. A reason, or null for "may, for all that"
107
+ */
108
+ unlocks?: Record<string, Message | null>;
109
+ /** The race they play (`raceOf`): left out in a game without races */
110
+ race?: string;
111
+ /**
112
+ * What the simulation's `available` hook decided, where it differs from what their race says (`availableTo`): by
113
+ * unit or structure type, and `upgrade:<id>`
114
+ */
115
+ availability?: Record<string, boolean>;
116
+ }
117
+ /**
118
+ * Whether a worker gathers a kind of resource at all (`harvester.kinds`): the game's `canHarvest` hook may refuse it a
119
+ * resource all the same (`canHarvest`)
120
+ *
121
+ * @beta
122
+ */
123
+ export declare const gathers: (def: Pick<UnitTypeDef, 'harvester'>, kind: string) => boolean;
124
+ /**
125
+ * Whether something of a race (`UnitTypeDef.race`, `UpgradeDef.race`) is a player's to make as their race goes: what is
126
+ * of no race is everyone's, and a player of none (the neutral players, the creeps, any in a game without races) may
127
+ * make anything. The `available` hook has the last word (`isAvailable`)
128
+ *
129
+ * @beta
130
+ */
131
+ export declare const availableTo: (def: {
132
+ readonly race?: string;
133
+ }, race: string | undefined) => boolean;
134
+ /**
135
+ * Whether a player may make something at all, as the simulation decided (`availability`, by `key`) or else as their
136
+ * race goes: what is not is left off their buttons
137
+ *
138
+ * @beta
139
+ */
140
+ export declare function availableToPlayer(def: {
141
+ readonly race?: string;
142
+ }, player: Pick<PlayerFacts, 'race' | 'availability'>, key: string): boolean;
143
+ /**
144
+ * Why something may not be made as far as what it requires goes: as the simulation decided (`unlocks`), or by the finished buildings it requires
145
+ *
146
+ * @beta
147
+ */
148
+ export declare function requirementRefusal(requires: readonly string[] | undefined, player: Pick<PlayerFacts, 'tech' | 'unlocks'>, key: string): Message | undefined;
149
+ /**
150
+ * What stands in the way of a cost, or undefined when the player can pay it
151
+ *
152
+ * @beta
153
+ */
154
+ export declare function costRefusal(resources: Readonly<Purse>, cost: Cost | undefined): Message | undefined;
155
+ /**
156
+ * Why a player cannot have a unit made, or undefined when they can, as far as they and the unit type go: whether
157
+ * the building has room, and what a game's hooks say (they can change the cost), is for the simulation. In the order the
158
+ * player is told
159
+ *
160
+ * @beta
161
+ */
162
+ export declare function trainRefusal(registry: Registry, def: UnitTypeDef, player: PlayerFacts, options?: {
163
+ cost?: boolean;
164
+ tech?: boolean;
165
+ }): Message | undefined;
166
+ /**
167
+ * What a shop pays for an item: a part of its price, and of what is left of it for what runs out
168
+ *
169
+ * @beta
170
+ */
171
+ export declare function sellValue(registry: Registry, item: string, charges: number): number;