fix(M01): correct ADT filename coordinate axes
Work-Package: M01-FND-COORD-TILE-AXIS-002 Agent: sindo-main-codex Tests: coordinate mapper, M00 calibration, baseline manifest, coordination and documentation gates passed Fidelity: Azeroth_31_49 raw MCNK origins and OpenRealm confirm filename X from world Y and filename Y from world X
This commit is contained in:
@@ -2,7 +2,7 @@
|
||||
|
||||
- Status: Accepted for M01 contract implementation
|
||||
- Date: 2026-07-13
|
||||
- Work package: `M01-FND-COORDS-001`
|
||||
- Work packages: `M01-FND-COORDS-001`, corrected by `M01-FND-COORD-TILE-AXIS-002`
|
||||
- Decision owners: M01 foundation/integration owners
|
||||
|
||||
## Context
|
||||
@@ -45,8 +45,8 @@ ADT_TILE_SIZE_YARDS = 1600 / 3
|
||||
ADT_TILES_PER_MAP_AXIS = 64
|
||||
WOW_WORLD_HALF_EXTENT_YARDS = 32 * ADT_TILE_SIZE_YARDS
|
||||
|
||||
tileX = floor(32 - canonical.X / ADT_TILE_SIZE_YARDS)
|
||||
tileY = floor(32 - canonical.Y / ADT_TILE_SIZE_YARDS)
|
||||
tileX = floor(32 - canonical.Y / ADT_TILE_SIZE_YARDS)
|
||||
tileY = floor(32 - canonical.X / ADT_TILE_SIZE_YARDS)
|
||||
```
|
||||
|
||||
`AdtTileCoordinate(tile_x, tile_y)` always means the indices in
|
||||
@@ -55,9 +55,9 @@ south-east extent produces index 64 and remains diagnosable as out of bounds.
|
||||
Normal valid indices are 0 through 63.
|
||||
|
||||
An `AdtTileLocalPosition` is measured east and south from the tile's
|
||||
north-west corner. An `AdtChunkCoordinate` uses `chunk_x` south and `chunk_y`
|
||||
east, with valid indices 0 through 15. These direction names avoid pretending
|
||||
that ADT file axes are Godot X/Z axes.
|
||||
north-west corner. Filename `tile_x` and MCNK `chunk_x` grow east; filename
|
||||
`tile_y` and MCNK `chunk_y` grow south, with valid indices 0 through 15. These
|
||||
direction names avoid pretending that ADT file axes are Godot X/Z axes.
|
||||
|
||||
### ADT placement fields
|
||||
|
||||
@@ -97,6 +97,17 @@ normalize the value to `[-PI, PI)` without adding an offset.
|
||||
This identity applies to world-facing yaw only. It does not apply to M2/WMO
|
||||
asset axes or placement Euler triples.
|
||||
|
||||
### Contract version 2 correction evidence
|
||||
|
||||
Contract version 1 incorrectly calculated filename `tile_x` from canonical X
|
||||
and `tile_y` from canonical Y. The private WotLK corpus contains the observed
|
||||
Elwynn point in `Azeroth_31_49.adt`, SHA-256
|
||||
`18185B5FAC9566D9C57A9C19ABD75F108370D1795639B6077167C0EFD3672FAE`; the
|
||||
transposed `Azeroth_49_31.adt` does not exist. Raw MCNK headers in that file
|
||||
show `indexX` decreasing world Y (east) and `indexY` decreasing world X (south).
|
||||
OpenRealm independently calculates filename X from world Y and filename Y from
|
||||
world X. Contract version 2 corrects the formulas before any consumer migration.
|
||||
|
||||
## Alternatives considered
|
||||
|
||||
### Make renderer coordinates canonical
|
||||
@@ -140,6 +151,8 @@ grid ownership rules.
|
||||
checkpoints within `0.002` yard.
|
||||
- Server, ADT placement, Godot and tile-local conversions round-trip.
|
||||
- Exact center, tile, chunk and world-extent boundaries have explicit tests.
|
||||
- The observed Elwynn position resolves to the real `Azeroth_31_49.adt` file;
|
||||
MCNK `(0,0)` to `(15,15)` origins confirm X-east and Y-south chunk growth.
|
||||
- World-yaw normalization and round-trip cases cover cardinal angles and wrap.
|
||||
|
||||
## References
|
||||
|
||||
@@ -5,10 +5,10 @@
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Status | Implemented |
|
||||
| Target/work package | `M01-FND-COORDS-001` |
|
||||
| Target/work package | `M01-FND-COORDS-001`, `M01-FND-COORD-TILE-AXIS-002` |
|
||||
| Owners | Foundation/domain |
|
||||
| Last verified | Worktree `work/sindo-main-codex/m01-coordinate-mapper`, 2026-07-13 |
|
||||
| Profiles/capabilities | All profiles; contract version 1 |
|
||||
| Last verified | Worktree `work/sindo-main-codex/m01-coordinate-tile-axis-fix`, 2026-07-13 |
|
||||
| Profiles/capabilities | All profiles; contract version 2 |
|
||||
|
||||
## Purpose
|
||||
|
||||
@@ -63,7 +63,7 @@ Forbidden dependencies:
|
||||
| `GodotWorldPosition` | Immutable value | Godot east/up/south scalars | Any thread; caller-owned reference | Does not create `Vector3` |
|
||||
| `AdtTileCoordinate` | Immutable value | `Map_tileX_tileY.adt` indices | Any thread; caller-owned reference | `is_within_map_grid()` reports invalid indices |
|
||||
| `AdtTileLocalPosition` | Immutable value | East/height/south offsets from tile north-west corner | Any thread; caller-owned reference | Values are intentionally unclamped |
|
||||
| `AdtChunkCoordinate` | Immutable value | MCNK chunk indices inside one tile | Any thread; caller-owned reference | `is_within_map_grid()` reports invalid indices |
|
||||
| `AdtChunkCoordinate` | Immutable value | MCNK X-east/Y-south indices inside one tile | Any thread; caller-owned reference | `is_within_map_grid()` reports invalid indices |
|
||||
| `CanonicalWowWorldYaw` | Immutable value | Canonical world yaw in radians | Any thread; caller-owned reference | Constructor does not normalize |
|
||||
| `ServerWorldYaw` | Immutable value | Movement orientation in radians | Any thread; caller-owned reference | Constructor does not normalize |
|
||||
| `GodotWorldYaw` | Immutable value | Godot Y-axis world yaw in radians | Any thread; caller-owned reference | Constructor does not normalize |
|
||||
@@ -97,7 +97,7 @@ Side effects:
|
||||
flowchart LR
|
||||
Server[ServerWorldPosition X,Y,Z] -->|identity components| Canonical[CanonicalWowWorldPosition]
|
||||
ADT[AdtPlacementPosition X,height,Z] -->|half extent - horizontal| Canonical
|
||||
Canonical -->|floor 32 - axis / tile size| Tile[AdtTileCoordinate]
|
||||
Canonical -->|tileX from Y; tileY from X| Tile[AdtTileCoordinate]
|
||||
Canonical -->|north-west edge offsets| Local[AdtTileLocalPosition]
|
||||
Local -->|floor offset / chunk size| Chunk[AdtChunkCoordinate]
|
||||
Canonical -->|half extent - Y; Z; half extent - X| Godot[GodotWorldPosition]
|
||||
@@ -139,7 +139,7 @@ There is no cancellation because every conversion is constant-time scalar math.
|
||||
|
||||
| Setting/capability | Default | Profile | Runtime mutable | Effect |
|
||||
|---|---|---|---|---|
|
||||
| Contract version | 1 | All | No | Axis, unit and boundary semantics in ADR 0001 |
|
||||
| Contract version | 2 | All | No | Corrected filename/chunk axes in ADR 0001 |
|
||||
| Godot units per WoW yard | 1 | `Blizzlike335` and current tools | No | Preserves current renderer scale |
|
||||
| ADT grid | 64 tiles/axis, 16 chunks/tile | WotLK 3.3.5a | No | Defines index and boundary math |
|
||||
|
||||
@@ -183,7 +183,7 @@ raw three-number arrays are not an accepted new persistence contract.
|
||||
|---|---|---|---|
|
||||
| Canonical/server/Godot position mapping | Implemented | Headless round-trip and five M00 golden points | Migrate producers/consumers |
|
||||
| ADT placement mapping | Implemented | Synthetic/direct round-trip fixtures | Compare native parsed placements during migration |
|
||||
| ADT tile/local/chunk ownership | Implemented | Center, extent, tile and chunk boundary fixtures | Migrate streaming names/ownership |
|
||||
| ADT tile/local/chunk ownership | Implemented | Center/extent boundaries plus raw `Azeroth_31_49.adt` filename and MCNK direction evidence | Migrate streaming consumers |
|
||||
| World-facing yaw mapping | Implemented | Cardinal/wrap round-trip fixtures | Placement Euler remains separate |
|
||||
| Scene-free production contract | Implemented | Source boundary and headless test | Add dependency search gate later in M01 |
|
||||
| Visual/server-spawn integration | Planned | M01 target criteria | Add golden server spawn after adapter migration |
|
||||
@@ -191,8 +191,8 @@ raw three-number arrays are not an accepted new persistence contract.
|
||||
## Known gaps and risks
|
||||
|
||||
- Existing native loaders and renderer scripts still contain manual conversions.
|
||||
- Current `StreamingWorldLoader` tile names may represent Godot X/Z ordering rather
|
||||
than ADT filename X/Y; migration must preserve visible baseline behavior.
|
||||
- Contract version 1 briefly transposed ADT filename/chunk axes; version 2 fixes
|
||||
the defect before any consumer migration.
|
||||
- MDDF/MODF rotation comments and implementations disagree across existing paths;
|
||||
this package deliberately does not generalize them into world yaw.
|
||||
- Finite-number validation belongs to external format adapters and is not yet implemented.
|
||||
|
||||
Reference in New Issue
Block a user