using System.Numerics; using Roboto.GameOffsets.States; namespace Roboto.Memory.States; /// /// Reads WorldData struct (168B, 1 RPM) and resolves the camera matrix. /// Primary camera source: WorldData.CameraPtr. Fallback: InGameState.CameraPtr (set via FallbackCameraPtr). /// public sealed class WorldDataState : RemoteObject { private WorldData _data; /// Camera pointer from InGameState, set by InGameStateReader before Update() is called. public nint FallbackCameraPtr { get; set; } public Matrix4x4? CameraMatrix { get; private set; } /// Resolved address of the camera matrix for hot-path caching. public nint CameraMatrixAddress { get; private set; } public WorldDataState(MemoryContext ctx) : base(ctx) { } protected override bool ReadData() { var mem = Ctx.Memory; var offsets = Ctx.Offsets; // Read the full WorldData struct (0xA8 = 168 bytes, 1 RPM) _data = mem.Read(Address); // Resolve camera: primary from WorldData, fallback from InGameState if (offsets.CameraMatrixOffset <= 0) return true; var camPtr = _data.CameraPtr; if (camPtr == 0) camPtr = FallbackCameraPtr; if (camPtr == 0) return true; var matrixAddr = camPtr + offsets.CameraMatrixOffset; CameraMatrixAddress = matrixAddr; var m = mem.Read(matrixAddr); if (float.IsNaN(m.M11) || float.IsInfinity(m.M11)) return true; CameraMatrix = m; return true; } protected override void Clear() { _data = default; FallbackCameraPtr = 0; CameraMatrix = null; CameraMatrixAddress = 0; } }