acdream/src/AcDream.Core/Physics
Erik f62a873be3 feat(phys): A6.P3 #98 Step 2 — cell-dump probe + roundtrip test
Step 2 of the apparatus plan at
C:\Users\erikn\.claude\plans\i-did-some-work-sharded-acorn.md. Adds a
one-shot cell-dump probe so the issue #98 replay harness can load real
cellar / cottage geometry as JSON fixtures, eliminating live-client
iteration from every fix attempt.

Probe gate:
  ACDREAM_DUMP_CELLS=0xA9B40143,0xA9B40146,0xA9B40147
  ACDREAM_DUMP_CELLS_DIR=tests/AcDream.Core.Tests/Fixtures/issue98 (default)

When set, the first time PhysicsDataCache.CacheCellStruct sees a matching
envCellId, it serializes the resulting CellPhysics to
<dir>/0x<cellid>.json and prints one [cell-dump] line. Zero cost when
unset (gate is a static-readonly IReadOnlySet<uint>.Count check).

DTOs (CellDump.cs):
- CellDump: top-level record holding cell id, WorldTransform,
  InverseWorldTransform, resolved polygons, portal polygons, portal
  infos, visible cell ids.
- PolygonDump / PortalDump / Vector3Dto / PlaneDto / Matrix4x4Dto:
  System.Text.Json-friendly records with explicit From / To converters.

What is intentionally NOT dumped: the DAT-native PhysicsBSPTree and
CellBSPTree trees. The replay harness drives the leaf-level walkable
predicates (WalkableHitsSphere, FindCrossedEdge, PolygonHitsSpherePrecise)
directly on the resolved polygon list, which is enough to expose the
issue #98 rejection (poly 0x0004 in 0xA9B40143 reports
insideEdges=False / overlapsSphere=False at the failing-frame sphere).
If a future replay needs BSP traversal we can extend the DTO + Hydrate
together without breaking fixtures.

Tests (CellDumpRoundTripTests):
- Capture → Hydrate preserves WorldTransform / InverseWorldTransform /
  every polygon's plane + vertices + NumPoints + SidesType.
- Capture → Hydrate preserves portal list + visible cell ids.
- Write to disk → Read back → Hydrate preserves content.
- Hydrate leaves BSP / CellBSP null by design (replay uses leaf-level
  predicates).

Verification:
- dotnet build: green, 0 errors.
- dotnet test: 1160 passed + 8 pre-existing failed (was 1156 + 8 before
  this commit; +4 from CellDumpRoundTripTests). Same 8 pre-existing
  failures, no new regressions.

Next: capture the three cells from the live client (Step 2 acceptance),
then build the replay harness against the fixtures (Step 3).
2026-05-23 15:16:56 +02:00
..
AnimationCommandRouter.cs fix(anim): Phase L.1b route motion commands 2026-04-28 10:46:22 +02:00
AnimationHookRouter.cs feat(anim): Phase E.1 hook router + GameWindow wiring 2026-04-18 16:30:23 +02:00
AnimationSequencer.cs fix(animation): close #61 + smooth stop from backward/sidestep-left/turn-left 2026-05-18 15:16:20 +02:00
BSPQuery.cs chore(phys): A6.P3 #98 triage — revert neg-poly + bldg-check experiments 2026-05-23 15:11:49 +02:00
BuildingPhysics.cs refactor(physics): Phase 2 — code-review polish on BuildingPhysics commit 2026-05-19 18:01:44 +02:00
CellDump.cs feat(phys): A6.P3 #98 Step 2 — cell-dump probe + roundtrip test 2026-05-23 15:16:56 +02:00
CellSurface.cs feat(core): Phase B.3 — CellSurface (indoor floor polygon projection) 2026-04-12 09:51:22 +02:00
CellTransit.cs chore(phys): A6.P3 #98 triage — revert neg-poly + bldg-check experiments 2026-05-23 15:11:49 +02:00
CollisionExemption.cs fix(phys L.2g slice 1b): widen CollisionExemption to ETHEREAL alone 2026-05-13 18:27:06 +02:00
CollisionPrimitives.cs feat(physics): port 9 collision primitives from acclient.exe (chunk_00530000.c) 2026-04-12 23:53:47 +02:00
EntityCollisionFlags.cs feat(physics): live-entity collision plumbing (Commit A) 2026-04-29 13:12:56 +02:00
IAnimationHookSink.cs feat(anim): Phase E.1 hook router + GameWindow wiring 2026-04-18 16:30:23 +02:00
InterpolationManager.cs feat(motion): L.3 M1 — fresh InterpolationManager port + retail spec 2026-05-05 14:56:42 +02:00
MotionCommandResolver.cs feat(anim): Phase L.1c select combat maneuvers 2026-04-28 11:44:17 +02:00
MotionInterpreter.cs fix(motion): retail-faithful remote tick — clear body.Velocity, drive via seqVel 2026-05-03 16:23:57 +02:00
PhysicsBody.cs docs(physics): L.3c attempt — friction threshold investigation, deferred 2026-04-30 09:46:42 +02:00
PhysicsDataCache.cs feat(phys): A6.P3 #98 Step 2 — cell-dump probe + roundtrip test 2026-05-23 15:16:56 +02:00
PhysicsDiagnostics.cs feat(phys): A6.P3 #98 Step 2 — cell-dump probe + roundtrip test 2026-05-23 15:16:56 +02:00
PhysicsEngine.cs fix(phys): A6.P3 slice 3 v3 — REVERT stickiness; hypothesis-test cellar-up 2026-05-22 12:43:58 +02:00
PlayerWeenie.cs feat(physics): PlayerWeenie with retail Run/Jump formulas 2026-04-13 23:15:25 +02:00
PortalInfo.cs feat(physics): Phase 2 — wire CellBSP + Portals into CellPhysics 2026-05-19 16:52:20 +02:00
PortalPlane.cs fix(core): Phase B.3 — add centroid + radius bounds to PortalPlane crossing test 2026-04-12 19:08:46 +02:00
PositionManager.cs fix(motion): project anim root motion onto terrain plane (slope staircase) 2026-05-05 21:37:42 +02:00
RemoteMoveToDriver.cs fix(retail): rotation rate, useability gate, retail toast strings 2026-05-16 12:17:54 +02:00
ResolveResult.cs feat(physics): L.3a — wall-bounce velocity reflection on airborne hits 2026-04-30 09:41:04 +02:00
ServerControlledLocomotion.cs fix(anim): Phase L.1c match MoveTo run speed 2026-04-28 20:58:22 +02:00
ShadowObjectRegistry.cs fix(physics): #91 — query indoor cell shadows in FindObjCollisions 2026-05-21 09:03:51 +02:00
TerrainSurface.cs fix(scenery): #49 9×9 loop, per-spawn building check, triangle slope 2026-05-07 21:15:11 +02:00
TransitionTypes.cs chore(phys): A6.P3 #98 triage — revert neg-poly + bldg-check experiments 2026-05-23 15:11:49 +02:00
WalkMissDiagnostic.cs feat(physics): WalkMissDiagnostic aggregator for ISSUES #83 probe spike 2026-05-20 10:31:39 +02:00