docs(phase): Indoor walking Phase 2 — Portal-based cell tracking shipped
Closes ISSUES.md #87 + #85 + the remaining wall-pass-through portion of #84 (fully closes #84). Portal-graph cell traversal replaces Phase D's AABB containment. Walking through doors promotes/demotes CellId correctly via portal traversal; walls block from inside indoor cells; indoor walkable plane is synthesized from the cell's floor poly so the resolver tracks walkability correctly during indoor movement. Files two new issues: #88 (indoor static objects vibrate — pre-existing, spotted during Phase 2 testing) and #89 (BSPQuery.SphereIntersectsCellBsp — follow-up to make CheckBuildingTransit retail-faithful; currently uses radius-less PointInsideCellBsp as a documented approximation). ISSUES.md: #87, #85, #84 moved to DONE. #88 + #89 filed. Roadmap: Indoor walking Phase 2 added to shipped table. CLAUDE.md: recent-phase paragraph updated to reflect Phase 2 shipped. New handoff: docs/research/2026-05-19-indoor-walking-phase2-shipped-handoff.md Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
eb0f772f0f
commit
a9c74d153a
4 changed files with 391 additions and 88 deletions
145
docs/ISSUES.md
145
docs/ISSUES.md
|
|
@ -237,9 +237,10 @@ to the second floor without getting stuck.
|
|||
|
||||
---
|
||||
|
||||
## #84 — Blocked by air indoors
|
||||
## #84 — [DONE 2026-05-19] Blocked by air indoors
|
||||
|
||||
**Status:** OPEN (partial fix 2026-05-19)
|
||||
**Status:** DONE
|
||||
**Closed:** 2026-05-19
|
||||
**Severity:** HIGH (blocks indoor navigation)
|
||||
**Filed:** 2026-05-19
|
||||
**Component:** physics, collision
|
||||
|
|
@ -274,58 +275,68 @@ enables the `FindEnvCollisions` indoor-BSP branch. This resolved the
|
|||
"spawn in building and be stuck above the floor" variant of #84 —
|
||||
player's CellId now promotes to the interior cell on spawn-in, the floor
|
||||
is walkable, and the player can move freely. The "invisible air obstacle"
|
||||
symptom for rooms the player walks INTO from outside is now superseded by
|
||||
the root cause in #87 (AABB containment is too tight for threshold/
|
||||
doorway cells to keep CellId promoted during normal walking). That
|
||||
remaining symptom will be resolved by the portal-based cell tracking
|
||||
fix.
|
||||
symptom for rooms the player walks INTO from outside was tracked under #87
|
||||
and required portal-based cell tracking.
|
||||
|
||||
**Resolution (2026-05-19 full · `1969c55, aad6976, 069534a, 702b30a, 3ffe1e4, eb0f772`):**
|
||||
Indoor walking Phase 2 replaced AABB containment with portal-graph cell traversal
|
||||
(`CellTransit.FindCellList` + `CheckBuildingTransit`). CellId now promotes to indoor
|
||||
cells via portals and remains promoted during normal walking through doorways. Indoor
|
||||
cell-BSP collision fires consistently. Indoor walkable plane synthesized from floor
|
||||
poly (`TryFindIndoorWalkablePlane`) so the resolver tracks walkability correctly when
|
||||
the player is standing on an indoor floor. User visually verified at Holtburg cottage:
|
||||
walls block from inside, multi-room navigation works, walking outdoors through a door
|
||||
works. Issue fully closed.
|
||||
|
||||
---
|
||||
|
||||
## #85 — Pass through walls from outside→in
|
||||
## #85 — [DONE 2026-05-19 · 1969c55, aad6976, 069534a, 702b30a, 3ffe1e4, eb0f772] Pass through walls from outside→in
|
||||
|
||||
**Status:** OPEN
|
||||
**Severity:** HIGH (gameplay-breaking)
|
||||
**Status:** DONE
|
||||
**Closed:** 2026-05-19
|
||||
**Commits:** `1969c55, aad6976, 069534a, 702b30a, 3ffe1e4, eb0f772`
|
||||
**Filed:** 2026-05-19
|
||||
**Component:** physics, collision
|
||||
|
||||
**Description:** Approaching a building from the outside, the player
|
||||
**Resolution (2026-05-19 · Indoor walking Phase 2):** The root cause (CellId never promoted
|
||||
to the indoor cell during outdoor→indoor walking) was resolved by portal-graph cell
|
||||
traversal in `CellTransit.CheckBuildingTransit`. Once `CellId` promotes to the indoor
|
||||
cell, the indoor-BSP collision branch in `FindEnvCollisions` fires for approaches from
|
||||
both inside and outside. User visually verified walls block from outside (player must
|
||||
use the door portal to enter). See #87 and handoff:
|
||||
[`docs/research/2026-05-19-indoor-walking-phase2-shipped-handoff.md`](2026-05-19-indoor-walking-phase2-shipped-handoff.md).
|
||||
|
||||
**Original description:** Approaching a building from the outside, the player
|
||||
can walk THROUGH walls into the interior — one-directional wall
|
||||
collision. From the inside trying to exit, the wall does block.
|
||||
|
||||
**Root cause / status:** Cell BSP polygons likely have one-sided
|
||||
normals (front-facing only). Approach from the inside hits the front;
|
||||
approach from the outside hits the back which BSP traversal treats as
|
||||
"behind the plane" → no collision. Retail handles this via two-sided
|
||||
collision polys or per-poly back-face handling.
|
||||
|
||||
**Files:**
|
||||
- `src/AcDream.Core/Physics/BSPQuery.cs`
|
||||
- `src/AcDream.Core/Physics/TransitionTypes.cs` (`FindObjCollisions` cell
|
||||
branch).
|
||||
|
||||
**Acceptance:** Walking into an inn wall from outside collides; player
|
||||
must enter via the door portal.
|
||||
|
||||
**Status update (2026-05-19):** The root cause is now pinned as the
|
||||
same failure as #84's remaining symptom — `CellId` isn't promoted to
|
||||
the indoor cell during normal outdoor→indoor walking because AABB
|
||||
containment is too tight for threshold/doorway cells. Without CellId
|
||||
in the indoor cell, the indoor-BSP collision branch in
|
||||
`FindEnvCollisions` never fires regardless of approach direction.
|
||||
See new issue #87 (portal-based indoor cell tracking) for the
|
||||
retail-faithful fix.
|
||||
The root cause was pinned (Cluster A 2026-05-19) as the same failure as
|
||||
#84's remaining symptom — `CellId` wasn't promoted to the indoor cell
|
||||
during normal outdoor→indoor walking because AABB containment was too
|
||||
tight for threshold/doorway cells. Without CellId in the indoor cell,
|
||||
the indoor-BSP collision branch in `FindEnvCollisions` never fired
|
||||
regardless of approach direction.
|
||||
|
||||
---
|
||||
|
||||
## #87 — Indoor cell tracking uses AABB containment instead of portal traversal
|
||||
## #87 — [DONE 2026-05-19 · 1969c55, aad6976, 069534a, 702b30a, 3ffe1e4, eb0f772] Indoor cell tracking uses AABB containment instead of portal traversal
|
||||
|
||||
**Status:** OPEN
|
||||
**Severity:** HIGH
|
||||
**Status:** DONE
|
||||
**Closed:** 2026-05-19
|
||||
**Commits:** `1969c55, aad6976, 069534a, 702b30a, 3ffe1e4, eb0f772`
|
||||
**Filed:** 2026-05-19
|
||||
**Component:** physics
|
||||
|
||||
**Description:** `PhysicsDataCache.TryFindContainingCell` promotes the
|
||||
**Resolution (2026-05-19 · Indoor walking Phase 2):** Portal-graph cell traversal
|
||||
(`CellTransit.FindCellList` + `CheckBuildingTransit`) replaced the AABB containment
|
||||
shortcut. Player CellId now correctly promotes to indoor cells via portals;
|
||||
indoor cell-BSP collision branch fires consistently; walls block from inside.
|
||||
Outdoor→indoor entry via `BuildingPhysics` + `BldPortalInfo` (`CheckBuildingTransit`)
|
||||
wires the building-shell portal graph. Indoor walkable plane synthesized from the
|
||||
cell's floor poly so the resolver tracks walkability during indoor movement (`TryFindIndoorWalkablePlane`).
|
||||
See handoff: [`docs/research/2026-05-19-indoor-walking-phase2-shipped-handoff.md`](2026-05-19-indoor-walking-phase2-shipped-handoff.md).
|
||||
|
||||
**Original description:** `PhysicsDataCache.TryFindContainingCell` promotes the
|
||||
player's `CellId` to an indoor EnvCell when their world position falls
|
||||
inside any cached cell's local AABB. This is too tight to keep `CellId`
|
||||
promoted to an indoor cell during normal walking. Threshold/doorway cells
|
||||
|
|
@ -338,34 +349,44 @@ physics is unreliable. The retail fix is portal-based cell traversal —
|
|||
when the player crosses a cell portal boundary, the cell ownership
|
||||
propagates through portal connectivity data in `CEnvCell`.
|
||||
|
||||
**Evidence:** `launch-cluster-a-cache-diag3.log` (Cluster A Phase E
|
||||
capture). Cell `0xA9B40143` (real room) has
|
||||
`physicsPolyCount=14 bspTotalLeafPolys=14 bspUnmatchedIds=0
|
||||
aabbMin=(-11.60,-1.60,0.00) aabbMax=(-6.20,7.60,2.80)` — geometry is
|
||||
complete and the AABB spans 2.8 m height, which works. Cell `0xA9B40146`
|
||||
(threshold/doorway) has `physicsPolyCount=4
|
||||
aabbMin=(-11.60,2.80,-0.20) aabbMax=(-10.00,7.60,0.00)` — Z range is
|
||||
only 0.2 m; a standing player is always outside it. Only 6 `[indoor-bsp]`
|
||||
lines fired across an entire indoor walking session (all during mid-jump
|
||||
frames when the player was briefly inside the room AABB at jump height).
|
||||
---
|
||||
|
||||
## #88 — Indoor static objects vibrate (bookshelves, open furnaces)
|
||||
|
||||
**Status:** OPEN
|
||||
**Severity:** MEDIUM (visual jitter; doesn't block gameplay)
|
||||
**Filed:** 2026-05-19
|
||||
**Component:** rendering, animation
|
||||
|
||||
**Description:** Static objects inside cells (bookshelves, open furnaces, possibly other interior props) show per-frame transform jitter / vibration. Pre-existing (user noticed before Phase 2 shipped). Likely candidates:
|
||||
|
||||
1. `EntityScriptActivator.OnCreate/OnRemove` firing repeatedly as the player's CellId promotes/demotes near cell boundaries (less likely after Phase 2's portal-based tracking — but worth investigating).
|
||||
2. Per-part transforms for cell-static `WorldEntity` instances getting recomputed each frame with floating-point drift.
|
||||
3. Particle-emitter offsets accumulating instead of resetting.
|
||||
|
||||
**Files to investigate:**
|
||||
- `src/AcDream.App/Rendering/Vfx/EntityScriptActivator.cs` — OnCreate/OnRemove call patterns
|
||||
- `src/AcDream.App/Rendering/GpuWorldState.cs` — entity transform updates per frame
|
||||
- `src/AcDream.App/Rendering/Wb/WbDrawDispatcher.cs` — per-batch transform composition
|
||||
|
||||
**Acceptance:** Indoor static objects render stable (no per-frame jitter).
|
||||
|
||||
---
|
||||
|
||||
## #89 — Port BSPQuery.SphereIntersectsCellBsp for retail-faithful CheckBuildingTransit
|
||||
|
||||
**Status:** OPEN
|
||||
**Severity:** LOW (Phase 2 ships with a documented approximation)
|
||||
**Filed:** 2026-05-19
|
||||
**Component:** physics
|
||||
|
||||
**Description:** Retail's `CEnvCell::check_building_transit` uses `CCellStruct::sphere_intersects_cell` — a radius-aware sphere-vs-BSP test that returns Inside/Crossing/Outside. Phase 2's `CellTransit.CheckBuildingTransit` uses `BSPQuery.PointInsideCellBsp` (radius-less, tests only the sphere CENTER). Practical effect: outdoor→indoor entry fires ~sphereRadius (~0.48m) deeper into the doorway than retail. The sphereRadius parameter is plumbed through but currently unused.
|
||||
|
||||
**Files:**
|
||||
- `src/AcDream.Core/Physics/PhysicsDataCache.cs` (`TryFindContainingCell`,
|
||||
approximately line 261)
|
||||
- `src/AcDream.Core/Physics/PhysicsEngine.cs` (`ResolveOutdoorCellId`,
|
||||
approximately line 238)
|
||||
- `src/AcDream.Core/Physics/TransitionTypes.cs` (`FindEnvCollisions` cell
|
||||
branch, approximately line 1188)
|
||||
- `src/AcDream.Core/Physics/CellTransit.cs::CheckBuildingTransit` (line ~162)
|
||||
- `src/AcDream.Core/Physics/BSPQuery.cs::PointInsideCellBsp` (line ~940) — existing point test to model the new sphere variant after
|
||||
|
||||
**Retail reference:** PDB symbols `CObjMaint::HandleObjectEnterCell` and
|
||||
`CEnvCell` portal data. See `docs/research/named-retail/acclient.h` lines
|
||||
31715-31726 for `CCellStructure` shape; `acclient_2013_pseudo_c.txt` for
|
||||
the implementations.
|
||||
|
||||
**Acceptance:** Player walking from outside the Holtburg cottage into the
|
||||
interior crosses portals and `CellId` updates accordingly; walls block
|
||||
from both inside and outside; the `[indoor-bsp]` probe fires consistently
|
||||
during indoor walking (not just during mid-jump frames).
|
||||
**Acceptance:** `CellTransit.CheckBuildingTransit` calls a new `BSPQuery.SphereIntersectsCellBsp(node, sphereCenter, sphereRadius)` that returns `Inside`/`Crossing`/`Outside`. Entry timing matches retail visually at the Holtburg cottage door.
|
||||
|
||||
---
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue