Shared run/bootstrap and development-arena lifecycle¶
Status: This is a historical design and batch record. The shared-scene foundation exists but is not a complete production scene. Follow the roadmap for the current shared-scene and integration plan.
R0 design deliverable, 2026-10-26. This continues the rebuild plan after the player/input contract. It defines ownership, entry/reset/exit order and a staged dummy arena. No class, scene, prefab, input package or gameplay change is implemented by this document. Proposed labels are responsibility names, not a framework or mandatory class hierarchy.
Implemented milestone and limits¶
Batch 35 verifies the isolated lifetime core (9/9 Editor groups). Batch 36 now supplies the minimal shared scene/host/bindings and Editor-only entry (7/7 import/PlayMode groups, exit0). F0's declared lifecycle/scene surface is verified: direct passive load, required binding validation, explicit activation, cancel/stop/fresh reset, actual reload and production dependency isolation. The scene contains no actors/content and remains outside production build lists. Full validated production requests/catalogs, player setup, clock/pool/event adapters and content integration remain with the owning phases; the F0 label is not a gameplay/whole-foundation acceptance claim.
Gameplay boundary and source evidence¶
Preserve the existing one/two-player mechanics, authored values, timing, formulas, reward/progression rules and movement feel. Approved extensions are explicit device-to-slot assignment, P1 keyboard-or-pad/P2–P4 pad-only, four-player capacity and button remapping. Additional-player participation rules must be designed explicitly; capacity does not authorize automatic balancing or payout changes. GAME-01 work and Tutorial-specific repairs remain parked.
The reference remains committed HEAD 5347e460 plus the current dirty source. Source pins and prior batch records are comparison evidence; they do not establish Steam equivalence. The scene wiring map records 38 direct YAML bootstrap/run components across all seven enabled scenes, their identities and selected references. It does not resolve every prefab-inherited component or prove runtime readiness.
| Existing path | Source-backed consequence for the rebuild |
|---|---|
| MainMenuManager.StartGame populates GameSession character list/player count, applies shop modifiers and loads the chosen scene. | Selection must produce a validated run request; preserve the selected characters, stage/difficulty and modifiers. Scene loading must not reconstruct choices from device order. |
| GameManager.Awake initializes state/PlayerManager from serialized arrays and constructs RewardRoller; Start pauses and asks GameInitialization to begin. | A run composition owner must supply these dependencies explicitly. A dummy arena cannot start a real player by bypassing this setup and assuming Awake filled all data. |
| GameInitialization imports/resets reward tables, assigns stage/spawn/manager data, activates pre-wired players and applies characters, registers camera/HUD, then yields OpenGate. | Preserve preparation dependencies while replacing boolean polling with explicit completion. Do not activate actors before their character/state/context is available. |
| GameManager.OpenGate waits 0.7 unscaled seconds, initializes menus, resumes, starts all three timers, starts the gate animation and shows UI after a further unscaled second. | Production entry/visible timing is baseline behavior to characterize. The development fixture can skip presentation through an explicit development entry policy; that does not change production timing. |
| AbilityHolder waits for characterInit; SpawnerEventManager waits for spawnerManagerInit and mutates SpawnEvent flags. | Readiness, cancellation and runtime state belong to the run. A permanently true stale flag or an infinite wait must not carry into retry. |
| Player.ApplyCharacter reads GameManager.Character[playerNumber], instantiates a weapon, reaches audio and starts asynchronous modifier setup. Entity.Awake reaches Camera.main/UIResourceProvider. | Player assembler must replace/bridge those dependencies coherently, including actual readiness. Do not mark player creation complete merely after SetActive or starting a coroutine. |
| PoolManager initializes in Start, uses stripped prefab names and activates reused objects before transform assignment. Enemy/Items/PlayerAttack use OnEnable for reset/spawn work. | Required transform/owner/runtime state must be supplied before activation. Migrate reset/registration consumers together; a new pool wrapper alone does not repair their lifecycle. |
| PlayerAttack.OnTriggerEnter2D directly gets Enemy; IDamageable alone is not its current universal target path. | A passive target cannot be declared compatible with existing projectiles simply by implementing IDamageable. Extract/adapt the real damage/target boundary before claiming combat acceptance. |
| GameManager.GameOver stops timers/spawns, computes progression, uses scaled waits, sends result/save work, animates UI and only calls PauseGame at the end. | Finishing is a sequence, not an immediate timeScale=0 state. Eager pausing can strand its scaled waits. Extract result persistence/presentation without changing their ordering or formulas. |
| GameManager.CheckGame explicitly inspects player[0]/player[1]; results/mastery/leaderboard/footstep stopping also contain two-player assumptions. | Map these consumers before extending slots. Mastery divides by two only when player count equals two; do not guess the intended three/four-player formula or backend schema. |
| GameMenuManager owns a transition guard and resumes before scene reload/return; CameraController adds targets and removes inactive transforms in Update. | Retry/return must dispose the old run once, preserve session/input selection and register the next actors once. Stale callbacks/targets must not affect the new run. |
| ServicesRoot creates AudioService and SaveService together; AppInitiator also initializes Steam, catalogs/settings and MainMenu startup. | The development fixture must compose required gameplay data/feedback without invoking the production boot/save/network chain. Direct static service calls are migration dependencies, not an excuse to load Bootloader. |
Shared scene and event direction · batch 30¶
The owner added shared gameplay-scene composition and scoped events to planning on 2026-10-26. Existing scene/behavior tables remain current-source evidence; this section describes the target, not an implementation.
One shared gameplay runtime scene hosts the composition/lifecycle, actors, camera/HUD bindings and common services. A validated stage/difficulty request supplies authored definition references; an environment prefab supplies geometry/tilemap/generator settings, bounds and named spawn markers resolved at runtime. Keep authored IDs, save/unlock keys, reward eligibility and existing scene-specific values intact. StageRunState owns timers, schedule cursors/flags, active boss/actors and generated-object cleanup. Unique behavior is an explicitly bound component; separate content composition needs a demonstrated requirement and reuses the same gameplay owners. The next stage contract must map actual scene overrides before old scene copies can retire.
Stage schema and binding requirements are designed in R0, the minimal shared scene/dummy launch in R1, full environment/encounter composition in R5b, remaining production content migration in R8. This separation avoids building every enemy/boss before player input works. The development fixture uses the same runtime with development-only request/data/adapters. It must not become a second gameplay scene whose managers later diverge.
The minimal event boundary starts in R1 with explicit application/run lifetime, typed payloads and owned subscriptions. Existing static GameEvents remains a compatibility adapter until producers and consumers migrate together. Add concrete notifications with each owner rather than inventing an all-purpose global bus up front. Direct commands/queries retain authoritative owners; events communicate facts at specified tested points. Carry run generation and relevant player/actor/instance identity, preserve current synchronous order and stat/achievement keys, avoid double delivery and reject old-run callbacks. Late observers query current state; disposing a run removes its listeners without clearing application listeners. Publish/readiness must follow dependency initialization, not determine it by subscription order. Producer/subscriber maps, re-entry/error policies and bridge removal checks remain R0 deliverables.
Responsibility, state and lifetime¶
| Responsibility | Owned data and lifetime | Required boundary |
|---|---|---|
| Session/roster | Player IDs, selected characters, assigned input sessions and binding profiles across scene handoffs/retry. | Defined in the player/input contract. No HP, spawned actor, reward count or run clock in persistent input/session state. |
| Validated run request | Requested stage/difficulty, roster IDs/character IDs, existing run/shop modifiers and execution mode (production/development). Snapshot taken at accepted start. | Definitions remain references/IDs; deep-copy mutable modifier values. StageMap persistent identity is preserved. Reject invalid/insufficient assignments before scene transition. |
| Stage bindings | Shared-scene camera/HUD bindings plus environment-owned bounds/spawn markers, presentation/resource references and explicitly required actor prefabs. Scene/environment lifetime. | One clear scene/composition entry point; no assumption that a child number, tag search or copied GameManager hierarchy provides the contract. |
| Run composition/lifetime | One run identity/generation, dependencies, participants/registrations, preparation status, cancellation and exit ownership. | May orchestrate smaller owners; does not become a new manager containing combat, rewards, persistence and UI code. No generic service locator/event framework is required. |
| Run state/clock policy | Authoritative menu/reward/game-over/stage state and timing policy for this run. | Input/UI request transitions; this owner applies the clock. Existing GameStateService is a candidate to retain/adapt, not proof its current setters cover every phase. |
| Actor runtime | Health/stamina/stats, ability/weapon cooldowns, target membership and active effects. Per actor/run. | Initialize/activate/deactivate/reset/dispose explicitly. Definitions are not mutated to reset a run. Death/revive does not destroy input identity. |
| Encounter/reward/progression runtime | Schedule cursors/flags, active encounter identity, queue/roll phase, upgrade counts, XP/score/currency earned in this run. | Separate owners; later contracts preserve current behavior. They publish results instead of formatting HUD or writing other owners' fields. |
| Registries/pool | Active actors/targets/projectiles/items, prefab identity and owned spawned objects. Run/scene lifetime unless a longer lifetime is explicitly justified. | Registration/removal happens once per activation/deactivation; prepare before active; return/despawn is idempotent. Do not use display names as authoritative pool identity. |
| Feedback/presentation | Camera/HUD/menu/audio adapters read runtime state and receive attributable events. | Explicitly optional or required by a declared fixture stage; no null-tolerant silent gameplay failure. Preserve production presentation behavior during its integration. |
| Result sink | Snapshot of completed run data; production progression/save/online adapters or a development capture-only sink. | Commit once per accepted run completion through the policy; a development completion cannot mutate normal progression or submit online data. Preserve production ordering and durability requirements. |
Input-session ownership is longer-lived than an actor; a pooled/dead/retried actor must not create another PlayerInput user. Run-owned callbacks include their run identity and are ignored after that lifetime ends. Static compatibility references may exist temporarily, but their owner and remaining callers must be recorded and they may only be cleared by the instance that installed them.
Preparation and entry protocol¶
- Accept request once. Validate execution mode, active slots, unique permitted assignments, selected content/unlocks, stage/difficulty data and required bindings. Capture run identity and a disposable cancellation/lifetime handle. Duplicate Start cannot create parallel runs.
- Compose dependencies without starting simulation. Resolve the approved catalog/definitions and current settings snapshot. Create run-owned state, registries and an initialized pool/spawn boundary. Choose production or development result/feedback policies explicitly. No time, combat, AI or encounter loop advances simply because a component enabled itself.
- Prepare runtime data. Create fresh encounter flags, reward inventories/counts, XP/stat counters and actor state from definitions. Preserve stage/reward eligibility and formulas. Do not reset shared ScriptableObject fields as an authoritative run reset. Subscribe run-owned listeners with paired cleanup.
- Prepare actors inactive. Obtain production actor prefabs, inject player IDs/character/input references, transforms and required capabilities; initialize stats, weapon/ability state and any child objects. Await actual initialization completion. Validate that source definitions are unchanged.
- Register and activate deliberately. Register actors/capabilities with camera/HUD/target consumers in an order consistent with their documented events. Publish activation only after context is complete; each event occurs once. Spawn helpers and OnEnable adapters must share that same protocol rather than both claiming initialization.
- Report Ready. Readiness means every required participant has completed, not that a coroutine has been launched or a field was set. Failure/cancellation prevents entry and identifies the missing/failed dependency without starting a partially wired run.
- Execute entry policy. Production retains its gate/resume/timer/UI sequencing until characterized equivalence is established. Development uses an explicit immediate-entry policy for the declared fixture stage; gameplay capability/timer semantics remain the same once Running begins. Consume old input button edges at handoff.
- Start supported systems once. Release the gameplay context and relevant clock/encounter loops together according to policy. A late readiness callback must not start a second timer or reinitialize actors. Systems excluded from an early fixture stage are explicitly absent and cannot masquerade as verified.
Component Awake may cache its own components; it must not require caller-supplied context that Unity has not yet provided. Use inactive construction and/or explicit Prepare before enable as appropriate. Do not set global script execution order as a substitute for an owned initialization dependency. Async/coroutine work needs explicit completion, failure and cancellation; diagnostic preparation time bounds must use an independent clock and not depend on paused simulation.
Run state and timing¶
The lifecycle records Preparing, Ready, Entering, Running, Finishing/Results, Exiting and Disposed for ownership/admission. These labels alone do not change gameplay. Menu pause/reward selection remain distinct reasons layered on the active run; they are not competing copies of one isPaused flag. Result/exit presentation has its current sequencing, rather than a new blanket rule that every non-Running phase instantly sets timeScale to zero.
| Situation | Required policy / behavior constraint |
|---|---|
| Preparation/readiness | No gameplay progression. UI/preparation/cancellation can continue with independent time. Production entry choreography is explicit and separate. |
| Running | Preserve existing simulation and distinct Timer clocks: currentGameTime, currentTime and difficulty-multiplied currentSpawnerTime. Do not merge clocks or apply multipliers to new domains. |
| Menu pause | Stop gameplay time according to existing policy; keep menu animations/input responsive. Cancel a child returns to its parent without resuming the run. |
| Reward selection | Preserve reward-owned pause, unscaled selection timing, queued-reward admission and active-player confirmation. Closing a menu does not clear reward ownership. |
| Finishing/results | Stop the timers/encounter work at the existing milestones. Preserve scaled/unscaled waits, result/achievement/save ordering and final pause. Characterize movement/abilities during this existing sequence before changing their gates. |
| Exit/retry | Accept one exit intent, consume input, run owned transition policy, detach old participants and restore the next scene's intentional clock state. Cancelled confirmations do not exit/resume an ended run. |
| Fixture shutdown / Editor check | Restore the caller's previous global clock and any scoped test state. Do not leave a paused Editor or stale static owner. Production return continues to its intentional normal clock state. |
A clock write is an owned policy action. Views, input adapters and independently destroyed objects must not unconditionally restore timeScale or clear other owners' pause reasons. Log lifecycle transitions/readiness failures through existing bounded diagnostics; do not add per-frame telemetry or restart GAME-01 investigation here.
Failure, reset and disposal protocol¶
A failed preparation cancels incomplete work, disables prepared-but-not-ready actors, removes registrations/listeners, returns/destroys only owned objects and reports failure. Retry from a failed preparation creates a fresh lifetime after cleanup; it does not toggle readiness flags and keep half the old state. Cleanup must be safe after every numbered preparation step, including before any actor exists.
For retry/reset/return:
- Admit one reset/exit; invalidate the old run generation and stop accepting new run commands/spawn/reward work.
- Cancel owned operations and transition callbacks at their defined boundary. A stale completion cannot load a second scene or hide a new overlay.
- Apply existing end/exit policy: normal reset/exit does not invent a new game-over payout. If completion was accepted, capture immutable results once and route through the appropriate result sink; development mode only captures them.
- Unsubscribe/disable run-bound event sources and consumers, unregister camera/HUD/targets, then deactivate actors/projectiles/enemies/items/effects. Complete cleanup required by pool contracts before return; guard re-entrant death/OnDisable/return events so they cannot duplicate rewards or enqueue an object twice.
- Dispose run-owned objects/registries and temporary compatibility references. Preserve application services, roster/input profiles and authored definitions. Clear a global only when it still refers to the disposing owner.
- For retry, build fresh runtime state from the same intended stage/difficulty/characters and retained input sessions. For menu return, release stage ownership and let the front-end entry owner activate its components. Restore the proper clock through the next owner, not a leftover actor.
Reset must cover HP/stamina/status/velocity, spawned weapons/companions/effects, cooldowns, target lists, event registrations, reward queue/selections/taken counts, XP/score/timers/schedule flags and result/exit admission. This list is a required scope audit, not permission to reset persistent currency/unlocks or alter existing run-start values. Stable profile/config data remains independent. Define which partial-run stats are intentionally persisted from actual current behavior during the progression contract; do not change it incidentally in teardown.
Development arena specification¶
Composition and isolation¶
After the R0 design gate, create the minimal shared gameplay runtime scene and supply a development-only stage request/configuration. A tiny development-only launcher may enter it directly; it contains no duplicated gameplay managers. The runtime has one composition/entry owner, a camera/bounds, spawn anchors for up to four planned slots, a flat movement surface/collider setup, a minimal status/control readout, and an explicitly referenced production actor prefab/catalog subset when the enabled milestone requires it. Use simple existing visuals where practical. No production UI redesign, art generation or extra released stage is required.
The direct-load test config and production character/stage selection both produce the same validated run request. A development launch can override the target to the fixture without inserting it into the public stage/unlock catalog. Keep entry policies distinct: direct fixture entry can omit logos/gates; selecting a released stage cannot silently acquire fixture behavior.
The fixture must not initialize AppInitiator/Steam/Discord/LeaderboardManager or the production ServicesRoot save chain. Compose required data, temporary settings and feedback explicitly. If a not-yet-migrated production actor needs a compatibility adapter, record every static caller and scope it to this run; do not copy GameManager/TutorialManager and present that as an independent bootstrap. An unexpected persistence/network call is an isolation failure, not a silently swallowed success.
Development mode has no normal-profile writes, unlock/currency/achievement effects or score submissions. Assert zero calls at those boundaries and compare normal-profile paths/bytes for actual player verification. If a test needs persistence, supply an explicitly disposable path/profile; never rely only on an IsDevelopment boolean that deeper static callers can bypass. Exclude development launchers/config/dummy content from production builds and public catalogs; include them deliberately for a development artifact. The shared gameplay scene may ship once its released content is migrated. It must have no always-included reference to dummy/development assets, including indirect prefab/catalog/Resources dependencies. Validate build contents rather than assuming an unlisted scene or development flag prevents inclusion.
Progressive fixture coverage¶
| Milestone | What exists | What may be claimed |
|---|---|---|
| F0 · R1 composition/lifetime | Direct-load arena, explicit config/request validation, fresh run identity/state, initialize/cancel/reset/dispose and visible readiness. A passive target can test the shared lifecycle when its minimal contract is present. | Composition/isolation/lifecycle only. No claim that a production player, attack, reward or four-player gameplay already works. |
| F1 · R2 assignment/input/assembly | Input sessions/roster, slot assignment and remap profile path, production player assembly boundary with required legacy dependencies extracted/adapted. | Device/slot ownership and actual assembly readiness; movement/combat only for capabilities already integrated and checked. No dummy player motor as a substitute. |
| F2 · R3 motor/vitals | Shared player motor, health/stats/damage ownership and a passive target through the same damage boundary. | Movement/dash/stun/damage/death/reset equivalence against the existing mechanics. No automatic enemy AI or weapon compatibility claim. |
| F3 · R4 combat/abilities | Existing production weapon/one existing ability/attack path adapted to the shared target contract, then remaining released ability cases. | Actual damage attribution, reload/cooldown/cost/interruption and reuse. IDamageable implementation alone is insufficient while attacks still require Enemy. |
| F4 · R5 encounters | One simple enemy using production behavior/capabilities, short authored spawn/clear sequence, later representative special/boss cases. | Encounter/death/despawn/clear/reset behavior with stated counts; not a full released-stage playthrough. |
| F5 · R6 onward integration | Existing reward/XP/pickup/result paths, development triggers and production UI/selection adapters. | Only the scenarios actually exercised; production results persist only through the real production sink after its compatibility checks. |
Development controls may reset the fixture, spawn its target/enemy, or grant an existing reward when that subsystem is present. They are bounded development operations and excluded from production bindings/progression. Use production player, damage, lifecycle and state code; dummy enemy behavior is intentionally small but implements the same contracts. Do not recreate TutorialPlayer or a second reward/pool implementation in the scene.
Acceptance scenarios¶
- Valid direct load and validated selection-handoff produce the same request-owned characters, stage/difficulty and modifiers. Invalid/missing dependency/device/content data fails before simulation or external side effects.
- Cancel preparation after each stage and retry; duplicate Start/Ready/reset/exit requests have one owner/effect. Reset repeatedly in the same process and reload the scene at least twice without stale callbacks, users, camera targets, registrations or spawned children.
- Prepare a pooled object at a distinct new position/rotation with a distinct owner, then activate it; its first gameplay callback sees those values. Repeated deactivate/return is safe; reset removes stale effects/targets/coroutines and cannot duplicate rewards.
- Retain roster identity and intended bindings across actor death/revive/retry/scene handoff; verify P1 keyboard-or-pad and P2–P4 pad-only, explicit pad reassignment between slots, remaps and correct active-slot validation. Device simulation does not replace physical-controller checks.
- Verify separate menu/reward pause ownership, advancing/stopped timer values and independent UI time. Preserve production entry/end timing and result/cancel behavior through actual player observations, not just state booleans.
- Assert definition values unchanged across repeated runs and isolation boundaries untouched. Keep normal saves/online submissions disabled in the fixture by composition and observable guards.
- At each supported milestone, compare one/two-player mechanics to the source/behavior baseline. Exercise three/four-player capability isolation without inventing missing reward/mastery/leaderboard semantics; full acceptance waits for those decisions/contracts.
- A development artifact declares its source/build identity, included fixture scene/config and enabled milestone. A passing empty arena is not a passing full game or a release candidate.
These scenarios are required future evidence, not tests run by this document.
Migration decisions and required follow-up¶
| Existing area | Initial disposition and removal/validation condition |
|---|---|
| GameSession | Retain selection compatibility while roster/request ownership is implemented. Remove parallel mutable character/player-count authority only after MainMenu, retry, Tutorial and all run consumers migrate. |
| GameInitialization | Replace flag-driven preparation with explicit run-owned completion/cancellation. Preserve catalog/stage/reward eligibility and current start choreography through adapters until migrated. Old methods/flags retire only with their consumers. |
| GameManager | Extract composition/state/progression/presentation along their planned workstreams; do not replace it with another all-purpose bootstrap class. Current formulas and result timing remain reference cases. |
| GameStateService / Timer | Retain/adapt core semantics; define one clock-policy owner. Characterize finishing and pending-reward transitions before centralizing setters. Keep the distinct timer meanings and multipliers. |
| PoolManager and OnEnable consumers | Migrate preparation/activation/reset together. Names/Start timing are not authoritative identity/readiness. Include Enemy, Items, PlayerAttack and Entity lifecycle callers; do not widen the first slice to every pool optimization. |
| Player/PlayerModifier/AbilityHolder/PlayerWeapon | Explicit initialization and completion, actor capability split and input injection. Preserve stats/timing/formulas. A scene setup checklist must account for weapon child transforms/materials/resources and async readiness. |
| Camera/HUD registries | Register/unregister actual runtime participants once; adapt from fixed arrays to active roster IDs where required. Preserve existing camera behavior for the baseline; define the extra-slot presentation rather than assume two arrays suffice. |
| ServicesRoot/AppInitiator/static Save/GameEvents | Production boot remains an integration boundary. Development composes a small dependency subset and guarded result sink. Audit subscriber lifetimes and direct static calls before any claimed fixture isolation. |
| Tutorial | Remains an R8 consumer of shared systems. Batch 25 stays parked. Its duplicate actor scripts do not supply the new bootstrap implementation. |
The player motor/vitals/stats contract now records that boundary and its source comparison cases. The combat/ability contract was completed in batch 29. The stage/enemy/encounter/event core contract and static maps were completed in batch 31, retaining SE-01–SE-06 import/runtime/migration follow-ups. The reward/pickup/progression core contract was completed in batch 32; RP-01–RP-05 retain specific participation/payout/scarcity/application follow-ups. Batch 33 adds the persistence/input preferences/UI/service integration contract, including logical override schema, current formats/paths, result transaction requirements and online compatibility gates. Concrete package serialization, assignment/recovery UI bindings and platform/backend evidence remain PS-01–PS-05 follow-ups. Batch 34 now reconciles the checklist and specifies the first R1a files/metadata/rollback/verification; the remaining package, recovery, imported binding and external checks gate their affected migrations. Full three/four-player reward conflicts, mastery/payout participation, result/HUD layout and backend submission schema require explicit designs. Existing two-player-only branches are evidence of missing generalization, not permission to choose a new formula.
Batch 34 now specifies the exact first R1a lifetime slice and phase gates. Batch 35 now implements/verifies that new lifetime owner (9/9 Editor groups); existing scene/gameplay migration is still absent. Batch 36 now verifies R1b scene integration/isolation at its no-actor scope; the first R2 roster/device slice is next. Later input/player/combat/stage/reward/persistence gates remain mandatory.
Batch 37 now passes an explicit RosterRunParticipant through this same shared host. Device assignment validates and locks before activation, unlocks on release, and retains the session's players/users through fresh runs and actual scene reload. No actor is assembled and no complete production stage/unlock request is validated. Batch 38 adds SessionRunParticipant through the same host, retaining the session/user across actual scene reload. Preparation blocks commands, activation admits gameplay, and stop/release prevents reopening input until a fresh run activates it. Its 8/8 simulated-device checks do not establish a full F1 pass. Profile, actor and production consumer integration remain future owners.
Batch 49 provides the first production actor setup seam: explicit character/shop/ammo/audio inputs and a coroutine completion handle, without a second actor implementation. The legacy initializer keeps its existing timing; the shared host does not yet create/activate actors. Its next actor participant must own identity, preparation/cancellation/teardown and isolate remaining legacy OnEnable/Update dependencies before activation. Input-session ownership still outlives the actor; no new PlayerInput user should be created.
Prepared actor integration · batch 50¶
PlayerActorRunParticipant now consumes the existing host, locked roster/slot and prepared input session. It clones the production prefab under an inactive owned root, binds explicit Entity components/camera/material, drives the real character/stat iterator, settles the existing projection and keeps all legacy scripts/physics isolated. Request shop values are copied. Preparation/cancellation/failure tasks join correctly; release destroys actor/weapon objects and their instantiated materials. Input/user identity remains with the session across new actor lifetimes. Wrong selection/session/run ownership rejects before admission.
Batch 50 verifies 13 GPU/lifecycle groups plus the prior 22 character and seven scene groups. The Editor-only development controller uses explicit P1 device selection and a private runtime light, without serialized development dependencies in Gameplay.unity or a normal service bootstrap. Its conditional class is absent from the native player assembly. Activation currently exposes a rendered preview, not migrated gameplay modules. Motion, vitals/ability/attack activation and full actor death/revive remain open. Existing native scenes still use their legacy initializer; do not close F1/R3/R4 from this preparation boundary.
Explicit movement activation · batch 52¶
Batch 52 adds an opt-in movement module to PlayerActorRunParticipant. Its default inert mode preserves earlier lifecycle checks. Preparation adds/configures PlayerMovementDriver under the inactive owned actor and copies the selected character's dash-speed primitive; activation enables only this driver and the root Rigidbody2D before exposing the root. Release disables the module/zeros velocity before destroying the same owned objects/materials. The driver consumes the existing input session and one Player motor; it creates no extra input user. DevelopmentPlayerRun opts in without serializing fixture content into Gameplay.unity or shipping its Editor-only controller. Held session input survives actor preparation/retry and the tested scene reload with an external session owner; the session owns its clock/history. The development launcher itself is scene-owned and disposes its session on unload. Production cross-scene session composition is still an integration gate. Combat/collector/vitals/ScreenBounds Start/Update behaviours stay disabled; this does not guarantee suppression of Unity physics callbacks. Collision/collectible ownership still needs its explicit integration. This is active walking, not complete actor life/combat/F1.