@driftengine/script 3.61.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 (61) hide show
  1. package/LICENSE +202 -0
  2. package/NOTICE +9 -0
  3. package/README.md +81 -0
  4. package/dist/bindings/ai.d.ts +66 -0
  5. package/dist/bindings/ai.js +173 -0
  6. package/dist/bindings/animation.d.ts +13 -0
  7. package/dist/bindings/animation.js +177 -0
  8. package/dist/bindings/audio.d.ts +56 -0
  9. package/dist/bindings/audio.js +126 -0
  10. package/dist/bindings/behavior.d.ts +36 -0
  11. package/dist/bindings/behavior.js +101 -0
  12. package/dist/bindings/chemistry.d.ts +72 -0
  13. package/dist/bindings/chemistry.js +253 -0
  14. package/dist/bindings/core.d.ts +172 -0
  15. package/dist/bindings/core.js +814 -0
  16. package/dist/bindings/editor.d.ts +53 -0
  17. package/dist/bindings/editor.js +248 -0
  18. package/dist/bindings/entities.d.ts +73 -0
  19. package/dist/bindings/entities.js +339 -0
  20. package/dist/bindings/interface.d.ts +55 -0
  21. package/dist/bindings/interface.js +200 -0
  22. package/dist/bindings/navigation.d.ts +36 -0
  23. package/dist/bindings/navigation.js +255 -0
  24. package/dist/bindings/network.d.ts +51 -0
  25. package/dist/bindings/network.js +96 -0
  26. package/dist/bindings/render.d.ts +71 -0
  27. package/dist/bindings/render.js +143 -0
  28. package/dist/bindings/rollback.d.ts +41 -0
  29. package/dist/bindings/rollback.js +74 -0
  30. package/dist/bindings/sprites.d.ts +53 -0
  31. package/dist/bindings/sprites.js +186 -0
  32. package/dist/bindings/terrain.d.ts +54 -0
  33. package/dist/bindings/terrain.js +138 -0
  34. package/dist/bindings/xr.d.ts +56 -0
  35. package/dist/bindings/xr.js +155 -0
  36. package/dist/entityHost.d.ts +80 -0
  37. package/dist/entityHost.js +159 -0
  38. package/dist/host.d.ts +153 -0
  39. package/dist/host.js +233 -0
  40. package/dist/index.d.ts +21 -0
  41. package/dist/index.js +18 -0
  42. package/package.json +68 -0
  43. package/src/bindings/ai.ts +306 -0
  44. package/src/bindings/animation.ts +346 -0
  45. package/src/bindings/audio.ts +185 -0
  46. package/src/bindings/behavior.ts +181 -0
  47. package/src/bindings/chemistry.ts +548 -0
  48. package/src/bindings/core.ts +1604 -0
  49. package/src/bindings/editor.ts +393 -0
  50. package/src/bindings/entities.ts +550 -0
  51. package/src/bindings/interface.ts +300 -0
  52. package/src/bindings/navigation.ts +367 -0
  53. package/src/bindings/network.ts +178 -0
  54. package/src/bindings/render.ts +191 -0
  55. package/src/bindings/rollback.ts +110 -0
  56. package/src/bindings/sprites.ts +310 -0
  57. package/src/bindings/terrain.ts +180 -0
  58. package/src/bindings/xr.ts +272 -0
  59. package/src/entityHost.ts +219 -0
  60. package/src/host.ts +465 -0
  61. package/src/index.ts +41 -0
package/src/host.ts ADDED
@@ -0,0 +1,465 @@
1
+ /**
2
+ * The engine as a DriftScript host: a registry describing what it provides, and the map that binds
3
+ * a compiled module to the real implementations.
4
+ *
5
+ * **This package is the only place the language and the engine are coupled**, and this file is the
6
+ * only place in it that knows about both at once. `driftscript` imports no `@driftengine/*` at all,
7
+ * asserted three ways; everything the engine contributes arrives through here.
8
+ *
9
+ * ---
10
+ *
11
+ * ## Adding a binding when a track lands
12
+ *
13
+ * **A capability that exists and is not bound is a capability DriftScript cannot reach**, and
14
+ * nothing fails when one is missed — a script author simply finds the module refused and assumes
15
+ * the track has not shipped. That silence is why this note exists rather than a checklist somewhere
16
+ * else.
17
+ *
18
+ * When a track lands, or a package grows a public function a script would want:
19
+ *
20
+ * 1. **Describe it.** A `defineCapability` entry in `bindings/`: its parameters and return as type
21
+ * names, its effects, whether a `@deterministic` function may call it, and a sentence of
22
+ * documentation that hover will show.
23
+ * 2. **Implement it.** One entry in the module's implementation map. A binding is a *lookup*; if it
24
+ * needs the engine to grow a function, that function belongs in the package that owns the
25
+ * subsystem.
26
+ * 3. **Provide it.** Add the module to `ENGINE_MODULES`, or a target cannot link it.
27
+ * 4. **Check the trap.** If the TypeScript signature has an optional parameter whose absence
28
+ * produces a *wrong result* rather than an error, make it required here and say why — a script
29
+ * author is further from the subsystem than a TypeScript caller and meets it first.
30
+ * `bindings/animation.ts` is the worked example.
31
+ * 5. **Correct the table.** `docs/CAPABILITIES.md` names which modules DriftScript reaches, and
32
+ * `driftscript`'s own linker names which do not, and refuses them by name.
33
+ * Those two lists must agree; a test asserts it.
34
+ *
35
+ * A binding is cheap — a table entry and a lookup — and is the difference between a subsystem
36
+ * a consumer can script and one they can only call from TypeScript.
37
+ */
38
+ import type { AudioGraph, SoundRegistry } from '@driftengine/audio';
39
+ import {
40
+ BEHAVIOR_CAPABILITIES,
41
+ BEHAVIOR_MODULE,
42
+ BEHAVIOR_TYPES,
43
+ behaviorImplementation,
44
+ type BehaviorServices,
45
+ } from './bindings/behavior.ts';
46
+ import {
47
+ NAVIGATION_CAPABILITIES,
48
+ NAVIGATION_MODULE,
49
+ NAVIGATION_TYPES,
50
+ navigationImplementation,
51
+ type NavigationServices,
52
+ } from './bindings/navigation.ts';
53
+ import {
54
+ TERRAIN_CAPABILITIES,
55
+ TERRAIN_MODULE,
56
+ TERRAIN_TYPES,
57
+ terrainImplementation,
58
+ } from './bindings/terrain.ts';
59
+ import {
60
+ SPRITES_CAPABILITIES,
61
+ SPRITES_MODULE,
62
+ SPRITES_TYPES,
63
+ spritesImplementation,
64
+ } from './bindings/sprites.ts';
65
+ import {
66
+ INTERFACE_CAPABILITIES,
67
+ INTERFACE_MODULE,
68
+ INTERFACE_TYPES,
69
+ interfaceImplementation,
70
+ } from './bindings/interface.ts';
71
+ import {
72
+ EDITOR_CAPABILITIES,
73
+ EDITOR_MODULE,
74
+ EDITOR_TYPES,
75
+ editorImplementation,
76
+ } from './bindings/editor.ts';
77
+ import {
78
+ NETWORK_CAPABILITIES,
79
+ NETWORK_MODULE,
80
+ NETWORK_TYPES,
81
+ networkImplementation,
82
+ } from './bindings/network.ts';
83
+ import {
84
+ ROLLBACK_CAPABILITIES,
85
+ ROLLBACK_MODULE,
86
+ ROLLBACK_TYPES,
87
+ rollbackImplementation,
88
+ } from './bindings/rollback.ts';
89
+ import {
90
+ bindHost,
91
+ createRegistry,
92
+ defineTarget,
93
+ type CapabilityRegistry,
94
+ type DriftModule,
95
+ type TargetManifest,
96
+ } from 'driftscript';
97
+ import {
98
+ AI_CAPABILITIES,
99
+ AI_MODULE,
100
+ AI_TYPES,
101
+ aiImplementation,
102
+ type AgentRegistry,
103
+ type AiServices,
104
+ } from './bindings/ai.ts';
105
+ import {
106
+ AUDIO_CAPABILITIES,
107
+ AUDIO_MODULE,
108
+ AUDIO_TYPES,
109
+ audioImplementation,
110
+ } from './bindings/audio.ts';
111
+ import {
112
+ XR_CAPABILITIES,
113
+ XR_MODULE,
114
+ XR_TYPES,
115
+ xrImplementation,
116
+ type XrRuntime,
117
+ } from './bindings/xr.ts';
118
+ import {
119
+ RENDER_CAPABILITIES,
120
+ RENDER_MODULE,
121
+ RENDER_TYPES,
122
+ renderImplementation,
123
+ } from './bindings/render.ts';
124
+ import {
125
+ ANIMATION_CAPABILITIES,
126
+ ANIMATION_MODULE,
127
+ ANIMATION_TYPES,
128
+ animationImplementation,
129
+ } from './bindings/animation.ts';
130
+ import {
131
+ CAMERA_CAPABILITIES,
132
+ CAMERA_MODULE,
133
+ CORE_TYPES,
134
+ EVENTS_CAPABILITIES,
135
+ EVENTS_MODULE,
136
+ INPUT_CAPABILITIES,
137
+ INPUT_MODULE,
138
+ PERSISTENCE_CAPABILITIES,
139
+ PERSISTENCE_MODULE,
140
+ PHYSICS_CAPABILITIES,
141
+ PHYSICS_MODULE,
142
+ RANDOM_CAPABILITIES,
143
+ RANDOM_MODULE,
144
+ SCENE_CAPABILITIES,
145
+ SCENE_MODULE,
146
+ TIME_CAPABILITIES,
147
+ TIME_MODULE,
148
+ cameraImplementation,
149
+ eventsImplementation,
150
+ inputImplementation,
151
+ persistenceImplementation,
152
+ physicsImplementation,
153
+ randomImplementation,
154
+ sceneImplementation,
155
+ timeImplementation,
156
+ } from './bindings/core.ts';
157
+ import type { CoreServices } from './bindings/core.ts';
158
+ import {
159
+ ECS_CAPABILITIES,
160
+ QUERY_CAPABILITIES,
161
+ ECS_MODULE,
162
+ ENTITY_TYPES,
163
+ type EntityServices,
164
+ PREFAB_CAPABILITIES,
165
+ PREFAB_MODULE,
166
+ entitiesImplementation,
167
+ prefabImplementation,
168
+ } from './bindings/entities.ts';
169
+ import {
170
+ CHEMISTRY_CAPABILITIES,
171
+ CHEMISTRY_MODULE,
172
+ CHEMISTRY_TYPES,
173
+ type ChemistryServices,
174
+ chemistryImplementation,
175
+ } from './bindings/chemistry.ts';
176
+ import { registerStd, stdImplementations } from 'driftscript/std';
177
+
178
+ /**
179
+ * What the engine can provide. Everything wired; nothing that is not.
180
+ *
181
+ * `drift/core` is deliberately absent: §11 gives its provider as `startLoop` and `LoopHooks`, which
182
+ * are what *drives* a script rather than what a script calls. A module with nothing to call is not
183
+ * registered rather than registered empty.
184
+ */
185
+ export const ENGINE_MODULES: readonly string[] = [
186
+ AI_MODULE,
187
+ XR_MODULE,
188
+ ANIMATION_MODULE,
189
+ BEHAVIOR_MODULE,
190
+ AUDIO_MODULE,
191
+ CAMERA_MODULE,
192
+ CHEMISTRY_MODULE,
193
+ ECS_MODULE,
194
+ EDITOR_MODULE,
195
+ EVENTS_MODULE,
196
+ NETWORK_MODULE,
197
+ ROLLBACK_MODULE,
198
+ INPUT_MODULE,
199
+ NAVIGATION_MODULE,
200
+ PERSISTENCE_MODULE,
201
+ PHYSICS_MODULE,
202
+ RANDOM_MODULE,
203
+ RENDER_MODULE,
204
+ SCENE_MODULE,
205
+ SPRITES_MODULE,
206
+ TERRAIN_MODULE,
207
+ TIME_MODULE,
208
+ INTERFACE_MODULE,
209
+ ];
210
+
211
+ /**
212
+ * A registry describing this engine's capabilities.
213
+ *
214
+ * Built rather than exported as a constant, because a registry refuses a duplicate registration —
215
+ * two consumers sharing one module-level instance would be one consumer's startup failing on
216
+ * another's import. Cheap: a few dozen object literals.
217
+ */
218
+ export function engineRegistry(): CapabilityRegistry {
219
+ const registry = createRegistry();
220
+
221
+ /* The standard library first, because it belongs to the language rather than to this host and a
222
+ host that forgot it would produce scripts that fail on `math.clamp`. */
223
+ registerStd(registry);
224
+
225
+ for (const type of [
226
+ ...AI_TYPES,
227
+ ...AUDIO_TYPES,
228
+ ...ANIMATION_TYPES,
229
+ ...CHEMISTRY_TYPES,
230
+ ...CORE_TYPES,
231
+ ...ENTITY_TYPES,
232
+ ...BEHAVIOR_TYPES,
233
+ ...NAVIGATION_TYPES,
234
+ ...TERRAIN_TYPES,
235
+ ...SPRITES_TYPES,
236
+ ...INTERFACE_TYPES,
237
+ ...EDITOR_TYPES,
238
+ ...NETWORK_TYPES,
239
+ ...ROLLBACK_TYPES,
240
+ ...RENDER_TYPES,
241
+ ...XR_TYPES,
242
+ ]) {
243
+ registry.addType(type);
244
+ }
245
+ for (const capability of [
246
+ ...AI_CAPABILITIES,
247
+ ...ANIMATION_CAPABILITIES,
248
+ ...AUDIO_CAPABILITIES,
249
+ ...BEHAVIOR_CAPABILITIES,
250
+ ...CAMERA_CAPABILITIES,
251
+ ...CHEMISTRY_CAPABILITIES,
252
+ ...ECS_CAPABILITIES,
253
+ ...EDITOR_CAPABILITIES,
254
+ ...NETWORK_CAPABILITIES,
255
+ ...ROLLBACK_CAPABILITIES,
256
+ ...QUERY_CAPABILITIES,
257
+ ...EVENTS_CAPABILITIES,
258
+ ...INPUT_CAPABILITIES,
259
+ ...NAVIGATION_CAPABILITIES,
260
+ ...PERSISTENCE_CAPABILITIES,
261
+ ...PHYSICS_CAPABILITIES,
262
+ ...PREFAB_CAPABILITIES,
263
+ ...RANDOM_CAPABILITIES,
264
+ ...RENDER_CAPABILITIES,
265
+ ...XR_CAPABILITIES,
266
+ ...SCENE_CAPABILITIES,
267
+ ...SPRITES_CAPABILITIES,
268
+ ...INTERFACE_CAPABILITIES,
269
+ ...TERRAIN_CAPABILITIES,
270
+ ...TIME_CAPABILITIES,
271
+ ]) {
272
+ registry.add(capability);
273
+ }
274
+ return registry;
275
+ }
276
+
277
+ /**
278
+ * A target providing everything this engine has wired.
279
+ *
280
+ * A consumer that wants less passes its own list. **A consumer that wants more cannot** — the
281
+ * manifest may only name modules something provides, so a target claiming `drift/ecs` is refused
282
+ * at the manifest rather than at every call site.
283
+ */
284
+ export function engineTarget(name = 'driftengine'): TargetManifest {
285
+ return defineTarget(name, ENGINE_MODULES);
286
+ }
287
+
288
+ export interface HostServices extends CoreServices {
289
+ /**
290
+ * The agents a script may name, and what the two bridges answer for them.
291
+ *
292
+ * `agents` alone is a supported configuration: a host with no navigation graph and no session
293
+ * still gets `wake`, `consider`, `intentId` and `degraded`. The bridge sub-services are what
294
+ * `reachable`, `navigate`, `path` and `deciding` need, and a capability whose service is absent
295
+ * fails at the call saying which one to provide rather than answering falsely.
296
+ */
297
+ readonly ai?: AiServices;
298
+ /**
299
+ * The live session, if a host has one.
300
+ *
301
+ * Absent means `drift/xr` calls fail at the call naming the namespace, which is the bargain every
302
+ * optional service here makes. A stub would be worse than usual: a script asking where a head is
303
+ * and getting the origin cannot tell a headset at the world origin from no headset at all, and
304
+ * one of those is a scene that draws and the other is a scene nobody is in.
305
+ */
306
+ readonly xr?: XrRuntime;
307
+ readonly audio?: { readonly graph: AudioGraph; readonly registry: SoundRegistry };
308
+ /**
309
+ * The component types, and any prefabs, a script may name.
310
+ *
311
+ * Absent means a script's `drift/ecs` calls fail at the call with the namespace's own name in the
312
+ * error — the same bargain every other optional service makes, and the reason none of them is
313
+ * stubbed.
314
+ */
315
+ readonly entities?: EntityServices;
316
+ /**
317
+ * The chemistry world a script reads and writes.
318
+ *
319
+ * Absent means `drift/chemistry` calls fail at the call naming the namespace — the same bargain
320
+ * every other optional service makes, and the reason none of them is stubbed. A stub would make a
321
+ * script whose fire never lights indistinguishable from one whose chemistry is not connected.
322
+ */
323
+ readonly chemistry?: ChemistryServices;
324
+ /**
325
+ * The network scripts path over: a graph, and one search reused across every agent.
326
+ *
327
+ * Absent means `drift/navigation` calls fail at the call naming the namespace, like every other
328
+ * optional service. A stub would be worse here than elsewhere: an agent given a route of no nodes
329
+ * behaves exactly like one that arrived, so a world whose navigation was never connected would
330
+ * look like a world where every agent is already where it wants to be.
331
+ */
332
+ readonly navigation?: NavigationServices;
333
+ /**
334
+ * What a behaviour tick is handed.
335
+ *
336
+ * Absent means `drift/behavior` calls fail at the call naming the namespace. A stub is
337
+ * particularly bad here for the reason `doing` exists: an agent whose routine never runs looks
338
+ * exactly like one that is standing about because it has nothing to do.
339
+ */
340
+ readonly behavior?: BehaviorServices;
341
+ }
342
+
343
+ /**
344
+ * The implementation map a generated module's `__bind` receives.
345
+ *
346
+ * Keyed by logical module name, because that is what generated code looks up: `audio` in a `.drs`
347
+ * file is `$host['drift/audio']` in the output.
348
+ *
349
+ * **A service the consumer did not supply is absent rather than stubbed.** A module that binds it
350
+ * and then calls it fails at the call with the namespace's own name in the error, which is what the
351
+ * rule against silent no-ops asks for — a stub that quietly did nothing would make a script that
352
+ * plays no sound indistinguishable from one whose audio is not connected.
353
+ */
354
+ export function engineImplementations(services: HostServices): Record<string, unknown> {
355
+ /* The standard library is merged in rather than bound separately, because a module importing both
356
+ `std/math` and `drift/audio` receives one host object. Leaving it to a consumer would produce a
357
+ script that fails on `math.clamp` with the namespace undefined. */
358
+ const map: Record<string, unknown> = { ...stdImplementations() };
359
+
360
+ if (services.audio !== undefined) {
361
+ map[AUDIO_MODULE] = audioImplementation(services.audio.graph, services.audio.registry);
362
+ }
363
+ if (services.clocks !== undefined) map[TIME_MODULE] = timeImplementation(services.clocks);
364
+ if (services.entities !== undefined) {
365
+ map[ECS_MODULE] = entitiesImplementation(services.entities);
366
+ map[PREFAB_MODULE] = prefabImplementation(services.entities);
367
+ }
368
+
369
+ /*
370
+ * These four take their handle as an argument rather than from the host, so they need nothing
371
+ * supplied and are always available. A script passes the `Node` or the `Actions` it was given.
372
+ */
373
+ map[RANDOM_MODULE] = randomImplementation();
374
+ map[SCENE_MODULE] = sceneImplementation();
375
+ map[RENDER_MODULE] = renderImplementation();
376
+ map[PHYSICS_MODULE] = physicsImplementation();
377
+ map[CAMERA_MODULE] = cameraImplementation();
378
+ map[ANIMATION_MODULE] = animationImplementation();
379
+ map[EVENTS_MODULE] = eventsImplementation();
380
+ map[PERSISTENCE_MODULE] = persistenceImplementation();
381
+ /* **Unconditional, unlike the four below it.** Every terrain capability takes the field it is
382
+ asking about, so the module needs nothing from the host: a `Terrain` reaches a script through
383
+ `uses`, the way a `NavGraph` does. There is nothing for an absent service to make fail. */
384
+ map[TERRAIN_MODULE] = terrainImplementation();
385
+ /* Unconditional for the same reason: every capability takes the batch, sheet, map or tree it
386
+ acts on, so neither module needs anything from the host to answer. */
387
+ map[SPRITES_MODULE] = spritesImplementation();
388
+ map[INTERFACE_MODULE] = interfaceImplementation();
389
+ map[INPUT_MODULE] = inputImplementation();
390
+ /* And once more for `drift/editor`: every capability takes the gizmo it is asking about, which
391
+ reaches a script through `uses`. There is nothing for an absent service to make fail. */
392
+ map[EDITOR_MODULE] = editorImplementation();
393
+ /* And the two Track J surfaces: each capability takes the session or the rewind it asks about,
394
+ so neither needs anything from the host beyond the handle a script is given through `uses`. */
395
+ map[NETWORK_MODULE] = networkImplementation();
396
+ map[ROLLBACK_MODULE] = rollbackImplementation();
397
+
398
+ /* `drift/ai` needs a registry for the same reason `drift/audio` needs one: an opaque
399
+ handle has to enter a script through a capability, and which agents exist in a
400
+ scene is not something an engine can know. Absent means a script's `ai.agent` calls
401
+ resolve to nothing — the same bargain every other optional service makes. */
402
+ if (services.ai !== undefined) map[AI_MODULE] = aiImplementation(services.ai);
403
+ if (services.xr !== undefined) map[XR_MODULE] = xrImplementation(services.xr);
404
+
405
+ /* And `drift/chemistry` needs a world for the same reason: a `Chemistry` handle has to enter a
406
+ script through a capability, and which parcels exist in a scene is not something an engine can
407
+ know. */
408
+ if (services.chemistry !== undefined) {
409
+ map[CHEMISTRY_MODULE] = chemistryImplementation(services.chemistry);
410
+ }
411
+
412
+ /* And `drift/navigation` needs the network, for the reason above stated once more: which places
413
+ a world has and which of them connect is the world's, not the engine's. */
414
+ if (services.navigation !== undefined) {
415
+ map[NAVIGATION_MODULE] = navigationImplementation(services.navigation);
416
+ }
417
+
418
+ /* And `drift/behavior` needs to know what a tick is handed, which is the consumer's world. */
419
+ if (services.behavior !== undefined) {
420
+ map[BEHAVIOR_MODULE] = behaviorImplementation(services.behavior);
421
+ }
422
+
423
+ return map;
424
+ }
425
+
426
+ export type BindResult =
427
+ { readonly bound: true } | { readonly bound: false; readonly reason: string };
428
+
429
+ /**
430
+ * Give a loaded module its host, and refuse in words when the host cannot satisfy it.
431
+ *
432
+ * Checked against `__drift.requires` before anything is called, so a missing service is reported at
433
+ * bind time naming the module — rather than at the first capability call, deep in a frame, as an
434
+ * undefined property.
435
+ */
436
+ export function bindModule(module: DriftModule, services: HostServices): BindResult {
437
+ const implementations = engineImplementations(services);
438
+
439
+ const missing = module.info.requires.filter(
440
+ (required) => required.startsWith('drift/') && implementations[required] === undefined,
441
+ );
442
+ if (missing.length > 0) {
443
+ return {
444
+ bound: false,
445
+ reason:
446
+ `\`${module.info.module}\` requires ${missing.map((m) => `\`${m}\``).join(', ')}, which ` +
447
+ 'this host has not been given. Pass the service to `bindModule` before loading the module.',
448
+ };
449
+ }
450
+
451
+ /*
452
+ * Through `bindHost` rather than by calling `__bind` directly, because the runtime has to
453
+ * remember which host this module was bound to.
454
+ *
455
+ * `patchModule` re-binds the new version to it. Calling `__bind` here would bind this version and
456
+ * leave the next one with every namespace at `undefined` — which is what happened for as long as
457
+ * `__bind` has existed, invisible because the only module anything ever patched imported no
458
+ * capability at all.
459
+ *
460
+ * A module with no capability imports has no `__bind`; `bindHost` treats that as a no-op, because
461
+ * a consumer should not have to know which of its scripts happen to use one.
462
+ */
463
+ bindHost(module, implementations);
464
+ return { bound: true };
465
+ }
package/src/index.ts ADDED
@@ -0,0 +1,41 @@
1
+ /*! DriftEngine | Copyright 2026 Drift Technologies | Apache-2.0 | https://github.com/drftrun/driftengine */
2
+ /**
3
+ * `@driftengine/script` — the `drift/*` bindings, and the only place the engine and the language
4
+ * are coupled.
5
+ *
6
+ * `driftscript` is host-neutral and imports no `@driftengine/*` at all, which three separate
7
+ * mechanisms assert. Everything this engine contributes to the language arrives through this
8
+ * package: registry entries describing capabilities that already exist, and the implementations a
9
+ * host hands to a compiled module.
10
+ *
11
+ * **There is no new engine code here.** A binding is a description plus a lookup. If one needed the
12
+ * engine to grow a function, that function belongs in the package that owns the subsystem, and the
13
+ * binding then describes it like any other.
14
+ */
15
+ export {
16
+ AUDIO_CAPABILITIES,
17
+ AUDIO_MODULE,
18
+ AUDIO_TYPES,
19
+ audioImplementation,
20
+ } from './bindings/audio.ts';
21
+
22
+ export type { ChemistryServices } from './bindings/chemistry.ts';
23
+ export {
24
+ CHEMISTRY_CAPABILITIES,
25
+ CHEMISTRY_COMPONENT,
26
+ CHEMISTRY_MODULE,
27
+ CHEMISTRY_TYPES,
28
+ chemistryImplementation,
29
+ } from './bindings/chemistry.ts';
30
+
31
+ export type { ComponentRegistry, RegisteredModule } from './entityHost.ts';
32
+ export { assertHostShapes, registerEntityModule } from './entityHost.ts';
33
+
34
+ export type { BindResult, HostServices } from './host.ts';
35
+ export {
36
+ ENGINE_MODULES,
37
+ bindModule,
38
+ engineImplementations,
39
+ engineRegistry,
40
+ engineTarget,
41
+ } from './host.ts';