sky(phase-3d): fix time drift — WorldTime.TickSize is always 1.0
User reported the in-game sky time in acdream consistently trails retail's, even after Phases 3a-3c.1 aligned the DayGroup selection. Diagnosed it as a rate mismatch between our client-side extrapolation and the ACE server's tick advancement. ACE advances PortalYearTicks at 1.0 ticks per real-second: Timers.cs: PortalYearTicks += worldTickTimer.Elapsed.TotalSeconds Our WorldTime was using SkyDesc.TickSize (0.8 in the live Dereth dat) as the extrapolation rate: NowTicks = lastSync + elapsed * TickSize // with TickSize=0.8 Between the server's ~20s TimeSync gap, we fell 4 ticks behind. Every sync yanked us back, but in the window between syncs the sky interp was rendering at a stale (earlier) dayFraction — visible as "acdream is behind retail" when the user had retail running alongside. Root cause: we misread r12 §1.2's definition of SkyDesc.TickSize. Agent C's decompile (`docs/research/2026-04-23-sky-decompile-hunt-C.md` §5 and the 2026-04-23 sky-retail-verbatim synthesis §5) showed SkyDesc.TickSize is consulted at `FUN_005062e0:6241` as: _DAT_00842798 = SkyDesc.TickSize + _DAT_008379a8 // next deadline i.e. the per-frame sky-subsystem update PERIOD. It's a throttle, not a clock-rate multiplier. SkyDesc.LightTickSize=15 plays the same role for lighting interpolation (re-run every 15 real-seconds). Fix: remove the SkyDesc.TickSize → WorldTime.TickSize assignment. Keep WorldTime.TickSize at its default 1.0, matching the server's rate. SkyDesc.TickSize stays on the LoadedSkyDesc for a future Phase 4 port of the actual retail throttle logic. Build + 717 tests green. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
f466c337ce
commit
75ad74e0b3
1 changed files with 18 additions and 2 deletions
|
|
@ -877,10 +877,26 @@ public sealed class GameWindow : IDisposable
|
||||||
_loadedSkyDesc = AcDream.Core.World.SkyDescLoader.LoadFromRegion(region);
|
_loadedSkyDesc = AcDream.Core.World.SkyDescLoader.LoadFromRegion(region);
|
||||||
if (_loadedSkyDesc is not null)
|
if (_loadedSkyDesc is not null)
|
||||||
{
|
{
|
||||||
WorldTime.TickSize = _loadedSkyDesc.TickSize > 0 ? _loadedSkyDesc.TickSize : 1.0;
|
// Phase 3d: do NOT assign WorldTime.TickSize from
|
||||||
|
// SkyDesc.TickSize. Agent C's decompile (chunk_00500000.c:6241
|
||||||
|
// FUN_005062e0) shows SkyDesc.TickSize is the "next sky-tick
|
||||||
|
// deadline" period — a throttle — NOT a game-time
|
||||||
|
// advancement rate. ACE's server advances PortalYearTicks at
|
||||||
|
// 1.0 ticks per real-second (Timers.cs: `PortalYearTicks +=
|
||||||
|
// worldTickTimer.Elapsed.TotalSeconds`). Our client
|
||||||
|
// extrapolation between TimeSyncs must match: 1.0.
|
||||||
|
//
|
||||||
|
// Previous behavior: WorldTime.TickSize = 0.8 (from the live
|
||||||
|
// SkyDesc.TickSize). Between ~20s TimeSync gaps we fell 4
|
||||||
|
// ticks behind the server, producing a visible "acdream sky
|
||||||
|
// is behind retail" time-of-day mismatch (user-verified
|
||||||
|
// 2026-04-23).
|
||||||
|
WorldTime.TickSize = 1.0;
|
||||||
|
|
||||||
Console.WriteLine(
|
Console.WriteLine(
|
||||||
$"sky: loaded Region 0x13000000 — {_loadedSkyDesc.DayGroups.Count} day groups, " +
|
$"sky: loaded Region 0x13000000 — {_loadedSkyDesc.DayGroups.Count} day groups, " +
|
||||||
$"TickSize={_loadedSkyDesc.TickSize}, LightTickSize={_loadedSkyDesc.LightTickSize}");
|
$"SkyDesc.TickSize={_loadedSkyDesc.TickSize} (throttle, not rate), " +
|
||||||
|
$"LightTickSize={_loadedSkyDesc.LightTickSize}");
|
||||||
|
|
||||||
// Initial DayGroup roll using whatever WorldTime currently
|
// Initial DayGroup roll using whatever WorldTime currently
|
||||||
// has (either the hardcoded boot seed or a pre-arrived
|
// has (either the hardcoded boot seed or a pre-arrived
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue