Warp: restore the translocation-vortex look + fix texture-scroll precision collapse (task #52)
The death/respawn "blue whirlwind" (tsphere) now matches the original cabinet
photo (capture.png): a smooth spinning lavender vortex with a bright core.
Root cause of the long-standing "radial spokes" artifact was NOT the warp code
but a general engine bug: L4D3D::SetTextureScrolling computed its texture-matrix
offset as scrollDelta * absolute_time, which grows unbounded and collapses UV
float precision -> a smooth scrolled cloud shatters into grainy radial steps.
Wrapped with fmodf(..., 1.0f) (identical under REPEAT tiling, full precision).
This also cleans the scrolling bexp beam grit and any other SCROLL material.
Visual reconstruction (verified against the real 45-vtx TSPHERE.BGF bicone,
offline-rasterized then ported):
- view ON-AXIS (eye centred on the throat) + spin in place -> concentric rings
(decomp FUN_00453dc4 does spin-about-local-Z + submit; the port had stubbed it)
- bintA cloud through a WIDE lavender ramp at full contrast (drawn as SKY);
no geometry "bands", no log-polar twist, no off-axis tornado (all discarded)
- tessellate the 12-facet bicone smooth; isotropic + trilinear; ramp baked into
the texture and drawn SELECTARG1(TEXTURE) to avoid double-tinting
Env knobs (BT_WARP_*) default to the verified values; BT_WARP_SELFTEST/SELFSHOT
are an off-by-default visual-verification harness (backbuffer frame dump).
Docs: new context/translocation-warp.md (geometry/material/visual/lifecycle/env);
reconstruction-gotchas.md gains the accumulated-time precision-collapse bug class;
rendering.md / multiplayer.md / decomp-reference.md / CLAUDE.md cross-linked.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 4.8
parent
a35f321ba1
commit
0bfb3d4ab3
@@ -203,6 +203,27 @@ AVs. Fill gaps with a shared read-only pad member. Same for a class's `<Name>Att
|
||||
|
||||
---
|
||||
|
||||
## 13. Accumulated-time precision collapse (rate × absolute-time in a matrix)
|
||||
|
||||
Any matrix element (or coordinate) computed as **`rate × absolute_runtime`** grows without bound. Float
|
||||
has ~7 significant digits, so once the value is large its FRACTIONAL precision is gone — and if that
|
||||
value is then added to a per-pixel/per-vertex quantity, the result **quantizes into coarse steps**. The
|
||||
visible signature is a smooth field shattering into grainy stair-steps or radial "spokes" that get
|
||||
worse the longer the app runs (and are invisible right after launch).
|
||||
|
||||
- **Archetype (the translocation-warp spokes):** `L4D3D::SetTextureScrolling` set a texture-matrix
|
||||
translate `_31 = -scrollUDelta * targetRenderFrame` (targetRenderFrame = absolute time). Within
|
||||
seconds the UV offset was large enough that adding it to the per-pixel UV collapsed precision → the
|
||||
scrolled cloud rendered as radial grain. It degraded EVERY scrolling texture (beams `bexp`, exhaust),
|
||||
but the full-screen warp on black made it obvious. **Fix:** wrap into the periodic range —
|
||||
`fmodf(rate*time, period)` — identical under REPEAT tiling / rotation, but full precision. Prefer
|
||||
delta-time accumulators that you wrap each frame, over `rate*absolute_time`. [T2]
|
||||
- **Tell from a symptom:** if a smooth animated/scrolled surface looks progressively grainier or
|
||||
"steps" and a STILL/offline render of the same data is clean, suspect an unwrapped time accumulator,
|
||||
not the geometry, texture, or filter. (Cost most of task #52's visual effort — see [[translocation-warp]].)
|
||||
|
||||
---
|
||||
|
||||
## Diagnostic recipe (the standard loop)
|
||||
1. Read the RAW decomp `reference/decomp/all/part_*.c` for the `FUN_xxxx`.
|
||||
2. Map `FUN_`/`DAT_`/`this+0xNN` to engine symbols via BT headers + WinTesla MUNGA source +
|
||||
|
||||
Reference in New Issue
Block a user