incanto 0.29.0 → 0.31.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 (55) hide show
  1. package/bin/incanto-editor.mjs +101 -28
  2. package/dist/2d.d.ts +28 -6
  3. package/dist/2d.js +3 -3
  4. package/dist/3d.d.ts +81 -7
  5. package/dist/3d.js +4 -4
  6. package/dist/{audit-C6rMyict.js → audit-C4kmDK0o.js} +16 -0
  7. package/dist/{behavior-BAc0erXF.d.ts → behavior-D_jMpFh8.d.ts} +117 -55
  8. package/dist/{create-game-CNKXGfpr.js → create-game-DqOjMBUS.js} +61 -48
  9. package/dist/{create-game-CbuLWorm.js → create-game-z5XaB1p5.js} +27 -15
  10. package/dist/debug-draw-BM3DsvtT.js +18 -0
  11. package/dist/debug.d.ts +1 -1
  12. package/dist/debug.js +8 -3
  13. package/dist/{duplicate-BgtFrFo4.js → duplicate-KRPtUtzl.js} +1 -1
  14. package/dist/{editor-switch-B0wB_DSr.d.ts → editor-switch-BJb-CWfA.d.ts} +12 -1
  15. package/dist/editor.js +1346 -1231
  16. package/dist/{register-C44aSduO.js → environment-presets--DigHNg4.js} +42 -11
  17. package/dist/{gameplay-L05WgWd1.js → gameplay-BftxM_It.js} +14 -5
  18. package/dist/gameplay.d.ts +1 -1
  19. package/dist/gameplay.js +1 -1
  20. package/dist/index.d.ts +12 -3
  21. package/dist/index.js +6 -6
  22. package/dist/{loader-B242FF6N.d.ts → loader-BYBrqTxP.d.ts} +1 -1
  23. package/dist/{loader-BZqOKfI2.js → loader-BlaRQGaA.js} +482 -6
  24. package/dist/net.d.ts +1 -1
  25. package/dist/net.js +3 -3
  26. package/dist/{pathfinding-BwD974Ss.d.ts → pathfinding-BwhqPD3i.d.ts} +1 -1
  27. package/dist/{physics-2d-CCVTrKOd.js → physics-2d-D9wquBvK.js} +30 -4
  28. package/dist/{physics-3d-BZZLtwJu.js → physics-3d-CnPygVGo.js} +41 -5
  29. package/dist/react.d.ts +1 -1
  30. package/dist/react.js +1 -1
  31. package/dist/{register-MelqEdza.js → register-CUY284Is.js} +3 -3
  32. package/dist/{register-BTg0EM7s.js → register-Dzkd6-os.js} +56 -380
  33. package/dist/{register-DWcWq4QG.js → register-tkR_8tWg.js} +4 -4
  34. package/dist/{registry-BVJ2HbCn.js → registry-CJdGpT2V.js} +6 -2
  35. package/dist/{editor-switch-CAKlJMIY.js → teardown-ByzfDPyu.js} +83 -4
  36. package/dist/test.d.ts +2 -7
  37. package/dist/test.js +43 -14
  38. package/dist/vite.d.ts +87 -1
  39. package/dist/vite.js +262 -3
  40. package/editor/assets/{agent8-DEVkEa3d.js → agent8-o27_Y1xN.js} +1 -1
  41. package/editor/assets/{debug-zGAtpDF0.js → debug-DfcWX3uW.js} +3 -2
  42. package/editor/assets/index-C9fb5QcT.js +10696 -0
  43. package/editor/index.html +1 -1
  44. package/package.json +1 -1
  45. package/skills/incanto-editor.md +61 -8
  46. package/skills/incanto-physics-and-input.md +15 -0
  47. package/skills/incanto-verifying-your-game.md +68 -0
  48. package/templates-app/beacon-isle-3d/package.json +1 -1
  49. package/templates-app/beacon-isle-3d/vite.config.ts +7 -0
  50. package/templates-app/tps-3d/package.json +1 -1
  51. package/templates-app/tps-3d/vite.config.ts +7 -0
  52. package/templates-app/village-quest-3d/package.json +1 -1
  53. package/templates-app/village-quest-3d/vite.config.ts +7 -0
  54. package/dist/debug-draw-CZmOYjL2.js +0 -13
  55. package/editor/assets/index-Bx4UtWYY.js +0 -10586
@@ -1,10 +1,10 @@
1
- import { t as registerCoreNodes } from "./register-BTg0EM7s.js";
1
+ import { t as registerCoreNodes } from "./register-Dzkd6-os.js";
2
2
  import { t as IncantoError } from "./errors-BpWbnbb_.js";
3
3
  import { t as Rng } from "./rng-DP-SR7eg.js";
4
- import { i as getNodeSchema, l as registerNode } from "./registry-BVJ2HbCn.js";
4
+ import { i as getNodeSchema, l as registerNode } from "./registry-CJdGpT2V.js";
5
5
  import { t as createNoise2D } from "./noise-CGUMx44x.js";
6
6
  import { i as applyParticlePreset, r as PARTICLE_PRESET_NAMES, t as ParticleSim } from "./particle-sim-Bw7hB93B.js";
7
- import { A as Water3D, F as PhysicsBody3D, H as colliderFootDrop, I as RigidBody3D, L as StaticBody3D, M as WaterCutout3D, N as Area3D, P as CharacterBody3D, R as Node3D } from "./gameplay-L05WgWd1.js";
7
+ import { A as Water3D, F as PhysicsBody3D, H as colliderFootDrop, I as RigidBody3D, L as StaticBody3D, M as WaterCutout3D, N as Area3D, P as CharacterBody3D, R as Node3D } from "./gameplay-BftxM_It.js";
8
8
  import { n as splatWeights, t as buildHeightmap } from "./heightmap-CRK0M4jT.js";
9
9
  import { AdditiveBlending, AnimationClip, AnimationMixer, Box3, BoxGeometry, BufferAttribute, BufferGeometry, CanvasTexture, CapsuleGeometry, Color, ConeGeometry, CylinderGeometry, DataTexture, DirectionalLight, DoubleSide, DynamicDrawUsage, Euler, Group, IcosahedronGeometry, ImageBitmapLoader, InstancedBufferAttribute, InstancedMesh, LinearFilter, LoopOnce, LoopRepeat, Matrix4, Mesh, MeshBasicMaterial, MeshDepthMaterial, MeshPhysicalMaterial, MeshStandardMaterial, NearestFilter, NoBlending, NormalBlending, PerspectiveCamera, PlaneGeometry, PointLight, Points, PointsMaterial, Quaternion, QuaternionKeyframeTrack, RGBADepthPacking, RGBAFormat, RepeatWrapping, SRGBColorSpace, ShaderChunk, ShaderMaterial, SphereGeometry, Texture, TextureLoader, UniformsLib, UniformsUtils, Vector3, Vector4, VectorKeyframeTrack } from "three";
10
10
  import { clone } from "three/addons/utils/SkeletonUtils.js";
@@ -6068,7 +6068,7 @@ var ModelInstance3D = class extends Node3D {
6068
6068
  if (entry.claimedBy && entry.claimedBy !== this) {
6069
6069
  if (!this.warnedClaim) {
6070
6070
  this.warnedClaim = true;
6071
- console.warn(`incanto: VRM '${this.model}' is already displayed by another node — a VRM asset can back only one ModelInstance3D.`);
6071
+ this.diagnose("warn", `incanto: VRM '${this.model}' is already displayed by another node — a VRM asset can back only one ModelInstance3D.`);
6072
6072
  }
6073
6073
  return;
6074
6074
  }
@@ -6119,7 +6119,7 @@ var ModelInstance3D = class extends Node3D {
6119
6119
  const scale = size.y > 0 ? this.targetHeight / size.y : prev;
6120
6120
  if (scale < .05 || scale > 20) {
6121
6121
  this.fitGroup.scale.setScalar(1);
6122
- console.warn(`[incanto] ModelInstance3D '${this.name}': targetHeight fit measured an implausible scale (${scale.toFixed(2)}x) — skinned rigs defeat bounding-box measurement. Rendering at the model's authored scale instead.`);
6122
+ this.diagnose("warn", `[incanto] ModelInstance3D '${this.name}': targetHeight fit measured an implausible scale (${scale.toFixed(2)}x) — skinned rigs defeat bounding-box measurement. Rendering at the model's authored scale instead.`);
6123
6123
  } else this.fitGroup.scale.setScalar(scale);
6124
6124
  } else this.fitGroup.scale.setScalar(1);
6125
6125
  }
@@ -6193,7 +6193,7 @@ var ModelInstance3D = class extends Node3D {
6193
6193
  const cached = this.entry.retargeted.get(ref);
6194
6194
  if (cached) return cached;
6195
6195
  const result = retargetClipToVrm(source, anim.scene, this.entry.vrm);
6196
- if (result.skippedBones.length > 0) console.warn(`incanto: retarget '${ref}' skipped bones: ${result.skippedBones.join(", ")}`);
6196
+ if (result.skippedBones.length > 0) this.diagnose("warn", `incanto: retarget '${ref}' skipped bones: ${result.skippedBones.join(", ")}`);
6197
6197
  this.entry.retargeted.set(ref, result.clip);
6198
6198
  return result.clip;
6199
6199
  }
@@ -6258,7 +6258,7 @@ var ModelInstance3D = class extends Node3D {
6258
6258
  action.crossFadeFrom(this.currentAction, ANIM_CROSSFADE, warp);
6259
6259
  }
6260
6260
  this.currentAction = action;
6261
- } else console.warn(`incanto: model '${this.model}' has no animation '${this.animation}' — embedded: ${this.entry.animations.map((c) => c.name).join(", ") || "(none)"}; assets: ${assets.animationRefs().join(", ") || "(none)"}`);
6261
+ } else this.diagnose("warn", `incanto: model '${this.model}' has no animation '${this.animation}' — embedded: ${this.entry.animations.map((c) => c.name).join(", ") || "(none)"}; assets: ${assets.animationRefs().join(", ") || "(none)"}`);
6262
6262
  }
6263
6263
  /** The upper-body layer: masked clip on the `upperBodyRoot` subtree. */
6264
6264
  syncUpperAnimation(assets) {
@@ -6272,13 +6272,13 @@ var ModelInstance3D = class extends Node3D {
6272
6272
  const resolved = this.resolveClip(this.animationUpper, assets);
6273
6273
  if (resolved === "loading") return;
6274
6274
  if (!resolved) {
6275
- console.warn(`incanto: model '${this.model}' has no animation '${this.animationUpper}' for the upper layer.`);
6275
+ this.diagnose("warn", `incanto: model '${this.model}' has no animation '${this.animationUpper}' for the upper layer.`);
6276
6276
  this.playingUpper = this.animationUpper;
6277
6277
  return;
6278
6278
  }
6279
6279
  const variants = this.layerVariants(resolved);
6280
6280
  if (!variants) {
6281
- console.warn(`incanto: upperBodyRoot '${this.upperBodyRoot}' not found in '${this.model}' — upper layer skipped.`);
6281
+ this.diagnose("warn", `incanto: upperBodyRoot '${this.upperBodyRoot}' not found in '${this.model}' — upper layer skipped.`);
6282
6282
  this.playingUpper = this.animationUpper;
6283
6283
  return;
6284
6284
  }
@@ -8306,7 +8306,7 @@ var River3D = class River3D extends Node3D {
8306
8306
  if (gaps.length * 3 < this.rings.length) return;
8307
8307
  this.warnedCoverage = true;
8308
8308
  const worst = gaps.reduce((a, b) => b.wettedHalfWidth - b.carriedHalfWidth > a.wettedHalfWidth - a.carriedHalfWidth ? b : a);
8309
- console.warn(`[incanto] River3D '${this.name}': the course is too tight for the water it holds — ${gaps.length} of ${this.rings.length} stations leave bare channel beside the ribbon (worst at ${worst.along.toFixed(0)} m: ground wet to ${worst.wettedHalfWidth.toFixed(1)} m from the centre, a bend that can only carry ${worst.carriedHalfWidth.toFixed(1)} m). Fix by EASING THE BENDS in \`path\` (fewer, straighter points), NARROWING \`widths\` there, or placing standing water (a Water3D) if that reach is really a pool.`);
8309
+ this.diagnose("warn", `[incanto] River3D '${this.name}': the course is too tight for the water it holds — ${gaps.length} of ${this.rings.length} stations leave bare channel beside the ribbon (worst at ${worst.along.toFixed(0)} m: ground wet to ${worst.wettedHalfWidth.toFixed(1)} m from the centre, a bend that can only carry ${worst.carriedHalfWidth.toFixed(1)} m). Fix by EASING THE BENDS in \`path\` (fewer, straighter points), NARROWING \`widths\` there, or placing standing water (a Water3D) if that reach is really a pool.`);
8310
8310
  }
8311
8311
  warnedCoverage = false;
8312
8312
  rebuildIfNeeded(mesh) {
@@ -11878,4 +11878,35 @@ function registerNodes3D() {
11878
11878
  registerNode(CharacterBody3D);
11879
11879
  }
11880
11880
  //#endregion
11881
- export { DEFAULT_TERRAIN_TEXTURE_BASE as A, movementState as B, FLOWER_VARIETIES as C, BoneAttachment3D as D, BoneLookAt3D as E, MeshInstance3D as F, buildMeshGeometry as I, QUARTER_PITCH as L, terrainThemeLayers as M, Joint3D as N, Billboard3D as O, InstancedMesh3D as P, cameraRelative as R, resolveFlowerDensity as S, Camera3D as T, rigPose as V, DirectionalLight3D as _, Trail3D as a, DENSITY_PRESETS as b, findRiverCoverageGaps as c, riverStepFor as d, smoothCourse as f, LoftMesh3D as g, ModelInstance3D as h, Tree3D as i, TERRAIN_THEMES as j, Terrain3D as k, projectToRiver as l, Particles3D as m, VOXEL_PALETTE as n, River3D as o, traceDownhillPath as p, VoxelGrid3D as r, buildRiverRings as s, registerNodes3D as t, riverCarveChannels as u, OmniLight3D as v, CharacterController3D as w, Flowers3D as x, Foliage3D as y, keyboardIntensity as z };
11881
+ //#region src/3d/environment-presets.ts
11882
+ /**
11883
+ * drei-compatible environment presets: each name maps to a 1k HDRI (the exact
11884
+ * Poly Haven CC0 files @react-three/drei ships), so `preset="sunset"` lights the
11885
+ * same here. Served from the agent8 CDN (the only sanctioned external host, same
11886
+ * as the terrain splat) — set `environment.hdri` to override with your own URL.
11887
+ */
11888
+ const CDN = "https://agent8-games.verse8.io/assets/3D/default/textures/hdri";
11889
+ const ENVIRONMENT_PRESETS = {
11890
+ apartment: "lebombo_1k.hdr",
11891
+ city: "potsdamer_platz_1k.hdr",
11892
+ dawn: "kiara_1_dawn_1k.hdr",
11893
+ forest: "forest_slope_1k.hdr",
11894
+ lobby: "st_fagans_interior_1k.hdr",
11895
+ night: "dikhololo_night_1k.hdr",
11896
+ park: "rooitou_park_1k.hdr",
11897
+ studio: "studio_small_03_1k.hdr",
11898
+ sunset: "venice_sunset_1k.hdr",
11899
+ warehouse: "empty_warehouse_01_1k.hdr"
11900
+ };
11901
+ /** Resolve `environment.preset` / `environment.hdri` to the HDR url (or null). */
11902
+ function resolveEnvironmentHdri(env) {
11903
+ if (typeof env.hdri === "string" && env.hdri !== "") return env.hdri;
11904
+ if (typeof env.preset === "string") {
11905
+ const file = ENVIRONMENT_PRESETS[env.preset];
11906
+ if (!file) throw new Error(`Unknown environment preset '${env.preset}'. Available: ${Object.keys(ENVIRONMENT_PRESETS).join(", ")}.`);
11907
+ return `${CDN}/${file}`;
11908
+ }
11909
+ return null;
11910
+ }
11911
+ //#endregion
11912
+ export { Terrain3D as A, keyboardIntensity as B, resolveFlowerDensity as C, BoneLookAt3D as D, Camera3D as E, InstancedMesh3D as F, rigPose as H, MeshInstance3D as I, buildMeshGeometry as L, TERRAIN_THEMES as M, terrainThemeLayers as N, BoneAttachment3D as O, Joint3D as P, QUARTER_PITCH as R, Flowers3D as S, CharacterController3D as T, movementState as V, LoftMesh3D as _, Tree3D as a, Foliage3D as b, buildRiverRings as c, riverCarveChannels as d, riverStepFor as f, ModelInstance3D as g, Particles3D as h, VoxelGrid3D as i, DEFAULT_TERRAIN_TEXTURE_BASE as j, Billboard3D as k, findRiverCoverageGaps as l, traceDownhillPath as m, registerNodes3D as n, Trail3D as o, smoothCourse as p, VOXEL_PALETTE as r, River3D as s, resolveEnvironmentHdri as t, projectToRiver as u, DirectionalLight3D as v, FLOWER_VARIETIES as w, DENSITY_PRESETS as x, OmniLight3D as y, cameraRelative as z };
@@ -1,7 +1,7 @@
1
- import { _ as registerBehavior, f as Node, m as Behavior, n as loadScene } from "./loader-BZqOKfI2.js";
1
+ import { f as Node, g as Behavior, n as loadScene, y as registerBehavior } from "./loader-BlaRQGaA.js";
2
2
  import { t as IncantoError } from "./errors-BpWbnbb_.js";
3
3
  import { t as jsonClone } from "./json-BLk7H2Qa.js";
4
- import { r as effectiveOrder, t as duplicateNode } from "./duplicate-BgtFrFo4.js";
4
+ import { r as effectiveOrder, t as duplicateNode } from "./duplicate-KRPtUtzl.js";
5
5
  import { Color, CubeCamera, DepthTexture, DoubleSide, Euler, FloatType, Frustum, HalfFloatType, LinearMipmapLinearFilter, MathUtils, Matrix4, Mesh, MeshDepthMaterial, Object3D, PerspectiveCamera, Plane, PlaneGeometry, Quaternion, ShaderMaterial, Sphere, Vector2, Vector3, Vector4, WebGLCubeRenderTarget, WebGLRenderTarget } from "three";
6
6
  //#region src/3d/frustum.ts
7
7
  const scratchFrustum = new Frustum();
@@ -2367,6 +2367,15 @@ var Node3D = class Node3D extends Node {
2367
2367
  this.position[2] ?? 0
2368
2368
  ];
2369
2369
  }
2370
+ /**
2371
+ * @internal The backing object IF it has been built — never builds one.
2372
+ *
2373
+ * `_ensureObject3D()` is the wrong call during teardown: it allocates a mesh
2374
+ * for a node that never rendered, purely so the next line can dispose it.
2375
+ */
2376
+ get _builtObject3D() {
2377
+ return this._object3D;
2378
+ }
2370
2379
  /** @internal The backing three object (lazily created). */
2371
2380
  _ensureObject3D() {
2372
2381
  if (!this._object3D) {
@@ -3341,9 +3350,9 @@ var Water3D = class Water3D extends Node3D {
3341
3350
  } : null;
3342
3351
  }
3343
3352
  free() {
3344
- const mesh = this._ensureObject3D();
3345
- mesh.geometry?.dispose();
3346
- mesh.material?.dispose?.();
3353
+ const mesh = this._builtObject3D;
3354
+ mesh?.geometry?.dispose();
3355
+ (mesh?.material)?.dispose?.();
3347
3356
  this.cubeTarget?.dispose();
3348
3357
  this.cubeTarget = null;
3349
3358
  this.cubeCamera = null;
@@ -1,5 +1,5 @@
1
+ import { X as Node, l as PropSchema, n as BehaviorCtor, t as Behavior, v as Engine } from "./behavior-D_jMpFh8.js";
1
2
  import { c as JsonValue, s as JsonObject } from "./schema-CcoWb32N.js";
2
- import { $ as Node, l as PropSchema, n as BehaviorCtor, t as Behavior, v as Engine } from "./behavior-BAc0erXF.js";
3
3
 
4
4
  //#region src/gameplay/chase.d.ts
5
5
  /**
package/dist/gameplay.js CHANGED
@@ -1,2 +1,2 @@
1
- import { C as FollowCamera, D as Health, E as DamageOnContact, O as Collector, S as restartScene, T as phaseOf, _ as hitStop, a as Wander, b as GameFlow, c as Projectile, d as PathFollow, f as Oscillate, g as Cooldown, h as CameraShake, i as WaveSpawner, k as Chase, l as Pickup, m as Lifetime, n as registerGameplayBehaviors, o as Spawner, p as MoveTo, r as ZombieAI, s as ScoreKeeper, t as GAMEPLAY_BEHAVIORS, u as Patrol, v as screenFlash, w as DayNight, x as goToScene, y as Interactable } from "./gameplay-L05WgWd1.js";
1
+ import { C as FollowCamera, D as Health, E as DamageOnContact, O as Collector, S as restartScene, T as phaseOf, _ as hitStop, a as Wander, b as GameFlow, c as Projectile, d as PathFollow, f as Oscillate, g as Cooldown, h as CameraShake, i as WaveSpawner, k as Chase, l as Pickup, m as Lifetime, n as registerGameplayBehaviors, o as Spawner, p as MoveTo, r as ZombieAI, s as ScoreKeeper, t as GAMEPLAY_BEHAVIORS, u as Patrol, v as screenFlash, w as DayNight, x as goToScene, y as Interactable } from "./gameplay-BftxM_It.js";
2
2
  export { CameraShake, Chase, Collector, Cooldown, DamageOnContact, DayNight, FollowCamera, GAMEPLAY_BEHAVIORS, GameFlow, Health, Interactable, Lifetime, MoveTo, Oscillate, PathFollow, Patrol, Pickup, Projectile, ScoreKeeper, Spawner, Wander, WaveSpawner, ZombieAI, goToScene, hitStop, phaseOf, registerGameplayBehaviors, restartScene, screenFlash };
package/dist/index.d.ts CHANGED
@@ -1,8 +1,8 @@
1
+ import { $ as LogEntry, A as VoicePreset, B as SfxParams, C as RendererStats, D as SfxPlayOptions, E as SfxEngine, F as Vec3, G as MusicManager, H as SynthOptions, I as spatialGain, J as AudioBuses, K as MusicTrack, L as spatialPan, M as ROLLOFF_MODELS, N as RolloffModel, O as isAudioContextAvailable, P as SpatialParams, Q as SceneTree, R as SFX_PRESETS, S as GameStats, T as InputMap, U as synthSfx, V as SfxWave, W as MusicBackend, X as Node, Y as BusName, Z as NodeLifecycle, _ as registeredTypes, a as registerBehavior, b as Scheduler, c as PropDef, d as createNode, et as LogLevel, f as getNodeSchema, g as registerNode, h as mergeStaticSignals, i as getBehavior, j as Listener, k as Voice, l as PropSchema, m as getNodeType, n as BehaviorCtor, nt as Signal, o as registeredBehaviors, p as getNodeSignals, q as PlayMusicOptions, r as clearBehaviors, rt as SignalListener, s as NodeCtor, t as Behavior, tt as LogManager, u as clearRegistry, v as Engine, w as Scene, x as EngineStats, y as EngineOptions, z as SFX_PRESET_NAMES } from "./behavior-D_jMpFh8.js";
1
2
  import { a as Rng, c as JsonValue, d as jsonKind, i as SceneJson, l as jsonClone, n as NodeJson, o as JsonKind, r as SCENE_FORMAT, s as JsonObject, t as ConnectionJson, u as jsonEquals } from "./schema-CcoWb32N.js";
2
- import { $ as Node, A as SfxPlayOptions, B as spatialPan, C as RendererStats, D as LogManager, E as LogLevel, F as ROLLOFF_MODELS, G as SynthOptions, H as SFX_PRESET_NAMES, I as RolloffModel, J as MusicManager, K as synthSfx, L as SpatialParams, M as Voice, N as VoicePreset, O as InputMap, P as Listener, Q as BusName, R as Vec3, S as GameStats, T as LogEntry, U as SfxParams, V as SFX_PRESETS, W as SfxWave, X as PlayMusicOptions, Y as MusicTrack, Z as AudioBuses, _ as registeredTypes, a as registerBehavior, b as Scheduler, c as PropDef, d as createNode, et as NodeLifecycle, f as getNodeSchema, g as registerNode, h as mergeStaticSignals, i as getBehavior, j as isAudioContextAvailable, k as SfxEngine, l as PropSchema, m as getNodeType, n as BehaviorCtor, nt as SignalListener, o as registeredBehaviors, p as getNodeSignals, q as MusicBackend, r as clearBehaviors, rt as SceneTree, s as NodeCtor, t as Behavior, tt as Signal, u as clearRegistry, v as Engine, w as Scene, x as EngineStats, y as EngineOptions, z as spatialGain } from "./behavior-BAc0erXF.js";
3
- import { n as loadScene, t as LoadSceneOptions } from "./loader-B242FF6N.js";
3
+ import { n as loadScene, t as LoadSceneOptions } from "./loader-BYBrqTxP.js";
4
4
  import { n as ParticleSimConfig, r as ParticleView, t as ParticleSim } from "./particle-sim-CwJ5rI_P.js";
5
- import { a as AudioElementLike, i as gridFromRows, n as PathGrid, o as AudioPlayer, r as findPath, t as FindPathOptions } from "./pathfinding-BwD974Ss.js";
5
+ import { a as AudioElementLike, i as gridFromRows, n as PathGrid, o as AudioPlayer, r as findPath, t as FindPathOptions } from "./pathfinding-BwhqPD3i.js";
6
6
  import { i as auditScene, n as IncantoErrorCode, r as IncantoErrorDetails, t as IncantoError } from "./errors-1dXlIwoR.js";
7
7
 
8
8
  //#region src/core/audio/crossfade.d.ts
@@ -47,6 +47,15 @@ declare class WebAudioMusicBackend implements MusicBackend {
47
47
  */
48
48
  interface DebugLineSource {
49
49
  readonly dimension: "2d" | "3d";
50
+ /**
51
+ * The engine whose world these lines describe.
52
+ *
53
+ * A page can hold more than one at a time — the editor runs its edit engine
54
+ * and a preview engine side by side — and a renderer must draw ITS world, not
55
+ * whichever source happens to be first in a module-level Set. Without this,
56
+ * one leaked physics instance paints its frozen colliders over everybody.
57
+ */
58
+ readonly engine: object;
50
59
  /** Toggle at runtime: `physics.debugDraw = true`. */
51
60
  debugDraw: boolean;
52
61
  /**
package/dist/index.js CHANGED
@@ -1,12 +1,12 @@
1
- import { _ as registerBehavior, a as SCENE_FORMAT, c as SceneTree, d as resolveConstants, f as Node, g as getBehavior, h as clearBehaviors, i as serializeNode, l as CONST_REF_KEY, m as Behavior, n as loadScene, o as computeViewport, p as parseNodePath, r as Scene, s as resolveViewport, u as isConstRef, v as registeredBehaviors, y as Signal } from "./loader-BZqOKfI2.js";
2
- import { C as crossfadeGains, S as WebAudioMusicBackend, T as AudioBuses, _ as spatialPan, a as HudLayer, b as synthSfx, c as UiText, d as LogManager, f as InputMap, g as spatialGain, h as ROLLOFF_MODELS, i as UiDialogue, l as AudioPlayer, m as isAudioContextAvailable, n as Timer, o as UiBanner, p as SfxEngine, r as UiButton, s as UiBar, t as registerCoreNodes, u as Engine, v as SFX_PRESETS, w as fadeGain, x as MusicManager, y as SFX_PRESET_NAMES } from "./register-BTg0EM7s.js";
1
+ import { _ as clearBehaviors, a as SCENE_FORMAT, b as registeredBehaviors, c as SceneTree, d as resolveConstants, f as Node, g as Behavior, h as InputMap, i as serializeNode, l as CONST_REF_KEY, n as loadScene, o as computeViewport, p as parseNodePath, r as Scene, s as resolveViewport, u as isConstRef, v as getBehavior, x as Signal, y as registerBehavior } from "./loader-BlaRQGaA.js";
2
+ import { C as fadeGain, S as crossfadeGains, _ as SFX_PRESETS, a as HudLayer, b as MusicManager, c as UiText, d as LogManager, f as SfxEngine, g as spatialPan, h as spatialGain, i as UiDialogue, l as AudioPlayer, m as ROLLOFF_MODELS, n as Timer, o as UiBanner, p as isAudioContextAvailable, r as UiButton, s as UiBar, t as registerCoreNodes, u as Engine, v as SFX_PRESET_NAMES, w as AudioBuses, x as WebAudioMusicBackend, y as synthSfx } from "./register-Dzkd6-os.js";
3
3
  import { t as IncantoError } from "./errors-BpWbnbb_.js";
4
4
  import { t as Rng } from "./rng-DP-SR7eg.js";
5
- import { t as auditScene } from "./audit-C6rMyict.js";
5
+ import { t as auditScene } from "./audit-C4kmDK0o.js";
6
6
  import { n as jsonEquals, r as jsonKind, t as jsonClone } from "./json-BLk7H2Qa.js";
7
- import { a as getNodeSignals, c as mergeStaticSignals, i as getNodeSchema, l as registerNode, n as clearRegistry, o as getNodeType, r as createNode, u as registeredTypes } from "./registry-BVJ2HbCn.js";
7
+ import { a as getNodeSignals, c as mergeStaticSignals, i as getNodeSchema, l as registerNode, n as clearRegistry, o as getNodeType, r as createNode, u as registeredTypes } from "./registry-CJdGpT2V.js";
8
8
  import { t as createNoise2D } from "./noise-CGUMx44x.js";
9
- import { n as ORDER_GROUP_BASE, r as effectiveOrder, t as duplicateNode } from "./duplicate-BgtFrFo4.js";
9
+ import { n as ORDER_GROUP_BASE, r as effectiveOrder, t as duplicateNode } from "./duplicate-KRPtUtzl.js";
10
10
  import { i as applyParticlePreset, n as PARTICLE_PRESETS, r as PARTICLE_PRESET_NAMES, t as ParticleSim } from "./particle-sim-Bw7hB93B.js";
11
11
  import { i as resolveRendering, n as attachTouchControls, r as joystickVector, t as TouchControls } from "./touch-031PxtCR.js";
12
12
  //#region src/core/pathfinding.ts
@@ -295,6 +295,6 @@ function newUid() {
295
295
  //#endregion
296
296
  //#region src/index.ts
297
297
  /** Engine version. Kept in sync with package.json by the release pipeline. */
298
- const VERSION = "0.29.0";
298
+ const VERSION = "0.31.0";
299
299
  //#endregion
300
300
  export { AudioBuses, AudioPlayer, Behavior, CONST_REF_KEY, Engine, HudLayer, IncantoError, InputMap, LogManager, MusicManager, Node, ORDER_GROUP_BASE, PARTICLE_PRESETS, PARTICLE_PRESET_NAMES, ParticleSim, ROLLOFF_MODELS, Rng, SCENE_FORMAT, SFX_PRESETS, SFX_PRESET_NAMES, Scene, SceneTree, SfxEngine, Signal, Timer, TouchControls, UiBanner, UiBar, UiButton, UiDialogue, UiText, VERSION, WebAudioMusicBackend, applyParticlePreset, assetUrls, attachTouchControls, auditScene, clearBehaviors, clearRegistry, computeViewport, createNode, createNoise2D, createSaveStore, crossfadeGains, duplicateNode, effectiveOrder, fadeGain, findPath, getBehavior, getNodeSchema, getNodeSignals, getNodeType, gridFromRows, isAudioContextAvailable, isConstRef, joystickVector, jsonClone, jsonEquals, jsonKind, loadScene, mergeStaticSignals, newUid, parseNodePath, preloadUrls, registerBehavior, registerCoreNodes, registerNode, registeredBehaviors, registeredTypes, replay, resolveConstants, resolveRendering, resolveViewport, serializeNode, spatialGain, spatialPan, startRecording, synthSfx };
@@ -1,5 +1,5 @@
1
+ import { v as Engine, w as Scene } from "./behavior-D_jMpFh8.js";
1
2
  import { i as SceneJson } from "./schema-CcoWb32N.js";
2
- import { v as Engine, w as Scene } from "./behavior-BAc0erXF.js";
3
3
 
4
4
  //#region src/core/scene/loader.d.ts
5
5
  interface LoadSceneOptions {