StaticallStaticassertValidate an Enablement axes list (Climbable / Swimmable / Flyable
setAxes). Throws TypeError on a duplicate or empty-string
entry. where labels the throw with the calling setter.
StaticassertValidate an Enablement difficulty value (Climbable / Swimmable /
Flyable setDifficulty). Throws RangeError on a non-null,
non-positive, or non-finite value. where labels the throw with
the calling setter.
StaticbodyStaticcanBare body-plan + posture predicate. Doesn't consult exit /
enablement / conveyance — those live in canTraverseExit.
StaticcanRun the full mode-gate cascade against an actor + a pre-resolved
exit. Used by LocomotionControllerBase after MQL has resolved
the player's typed direction (or door alias) into target.via.exit.
Gate order (first failure surfaces):
Exit.canTraverse)getEnablementMixin)StaticcheckResolve the enablement gate for a mode. Three shapes:
getPassthrough()): walk the actor's slot
occupations looking for a host that composes the mode's
conveyanceMixin.enablementMixin (climb / swim / fly): walk the
actor's scope looking for a host that composes that mixin AND
accepts the direction AND can be engaged by the actor.{ ok: true }.StaticdefaultThree-layer chain for "what mode should this actor default to?":
movement.defaultMode setting (only for hosts
composing EnvironmentMixin — players who've customized).BodyPlan.defaultLocomotionMode)
— meaningful for NPCs (bird → fly, fish → swim, etc.). Skipped
for non-Organism actors.'walk'.ShellApi.resolveSetting('movement.defaultMode') is deliberately
NOT used — its built-in schema-default fallback to 'walk' would
short-circuit the bodyplan layer. ShellApi.ownSetting returns the
explicit override only.
StaticeligibleModes whose body-plan + posture gates an actor passes right now. Backs future verb-help / UI surfaces; does NOT consult exit or scope (those are per-traversal concerns).
StaticemissionWalk the passthrough chain to the host whose engaged mode is
non-passthrough, and return its emission data. Returns null if
the mover isn't Mobile, isn't engaged in anything, or the chain
runs out of valid hosts.
Cycle guard: MAX_PASSTHROUGH_DEPTH (16, mirrors Mobile.traverse's
conveyance ripple guard). Cycles aren't possible from any valid
runtime state — slot occupancy is a tree by construction — but
authored content can goof and produce a circular shape: e.g., two
Stuff that are each both Slotted and Slottable, where A's
mount slot holds B and B's mount slot holds A, both engaged in
ride. findConveyanceHost(A, ride) → B, then findConveyanceHost (B, ride) → A, etc. The guard caps the walk at 16 hops and
returns null rather than spinning forever — the legitimate
passthrough depths Saxonberg cares about (rider → horse → cart →
road, etc.) are nowhere near that bound.
StaticengageRun action with actor.engagedMode set to mode. After the
action resolves, clear engagedMode when the mode is transient
(per isTransientEngagement) — leave it set when persistent (the
actor is still in the engaged scope at the destination).
Errors from action propagate; the finally clause clears
engagement for transient modes regardless, ensuring no stale
engagedMode survives a failed traversal.
StaticengagedType-safe convenience for non-Mobile callers ("what mode is X
engaged in, if any?"). Returns null for non-Mobile Stuff.
StaticexitStaticfindWalk a single passthrough hop: given an actor engaged in a passthrough mode, find the conveyance host they're slotted into. Throws when called with a non-passthrough mode (programmatic misuse).
Staticis"Should engageAround clear engagedMode after the traversal?"
Slotted.vacate witness clears it on dismount.StaticloadAsync-lazy companion to modeOf / modeOfOrThrow. Awaits
StuffApi.singleton so the mode is cloned on first use, then
subsequent sync lookups (e.g., from Mobile.getEngagedMode,
Drivable.getVehicularMode) hit the cached singleton.
Use this from async caller paths that need the mode for the
first time — verb controllers, traverseWithDefault, anywhere
the lazy-design's first-touch happens. Pure registry hits stay
with the sync modeOf family.
StaticmodeResolve a LocomotionMode by short name (e.g. 'walk') or full
templatePath. Returns null when the singleton isn't loaded —
lazy resolution is intentional (avoids hard-pinning the nine
singletons in the bootstrap manifest).
StaticmodeStaticpostureStaticpreloadEnsure the actor's species + bodyplan singletons are live so the
sync eligibility cascade (bodyPlanAllows, postureAllows, etc.)
can read them via findByTemplatePath. Without this, a fresh
server's first organism-shaped go reports "Your body can't
walk." even for a Homo-sapiens-with-biped-bodyplan avatar — the
species is loaded by the requiresAnimate validator preload but
the bodyplan singleton was never touched.
No-op for non-Organism actors and for Organisms with no
_speciesPath / _bodyPlanPath — those skip the bodyplan gate
naturally per bodyPlanAllows.
Idiomatically paired with loadMode at locomotion entry points.
StaticresolvePick the mode a host is currently moving under. Resolution:
engagedMode (when non-null).vehicularMode (when Drivable). If the host IS
Drivable but vehicularMode is null, throw — Drivables
that ship without an authored vehicular mode are a content
authoring bug (e.g., a cart with no idea how it moves). Fail
loudly so the bug surfaces in dev rather than silently
walk-traversing a wheeled vehicle.StatictraverseResolve the actor's default mode (see defaultModeFor for the
chain) into the corresponding LocomotionMode singleton, then
traverse exit with full engagement bookkeeping via
engageAround. Convenience for programmatic callers that want
"use the actor's preferred mode" without resolving the singleton
themselves.
Throws on mode-gate failure (mirrors Mobile.traverse's contract).
Every live
LocomotionModesingleton. O(N) over the global registry; v1's universe is small enough that this is acceptable.