From d125fb2cd3ff50d6b1705b5eeb3eaba68f034d0d Mon Sep 17 00:00:00 2001 From: Jarrod Doyle Date: Tue, 27 Aug 2024 07:10:38 +0100 Subject: [PATCH] Parse lightmaps as flat array rather than multidimensional array --- project/code/LGS/Database/Chunks/WorldRep.cs | 39 +++++++++----------- project/code/TMV/Mission.cs | 6 +-- 2 files changed, 21 insertions(+), 24 deletions(-) diff --git a/project/code/LGS/Database/Chunks/WorldRep.cs b/project/code/LGS/Database/Chunks/WorldRep.cs index 5ea36a7..9423b35 100644 --- a/project/code/LGS/Database/Chunks/WorldRep.cs +++ b/project/code/LGS/Database/Chunks/WorldRep.cs @@ -97,45 +97,42 @@ public class WorldRep : IChunk public struct Lightmap { - public byte[,,,] Pixels { get; set; } + public byte[] Pixels { get; set; } + + public int Layers; + public int Width; + public int Height; + public int Bpp; public Lightmap(BinaryReader reader, byte width, byte height, uint bitmask, int bytesPerPixel) { var count = 1 + BitOperations.PopCount(bitmask); - Pixels = new byte[count, height, width, bytesPerPixel]; - for (var c = 0; c < count; c++) - { - for (var y = 0; y < height; y++) - { - for (var x = 0; x < width; x++) - { - for (var b = 0; b < bytesPerPixel; b++) - { - Pixels[c, y, x, b] = reader.ReadByte(); - } - } - } - } + var length = bytesPerPixel * width * height * count; + Pixels = reader.ReadBytes(length); + Layers = count; + Width = width; + Height = height; + Bpp = bytesPerPixel; } public readonly Vector4 GetPixel(uint layer, uint x, uint y) { - if (layer >= Pixels.GetLength(0) || x >= Pixels.GetLength(2) || y >= Pixels.GetLength(1)) + if (layer >= Layers || x >= Width || y >= Height) { return Vector4.Zero; } - switch (Pixels.GetLength(3)) + var idx = 0 + x * Bpp + y * Bpp * Width + layer * Bpp * Width * Height; + switch (Bpp) { case 1: - var raw1 = Pixels[layer, y, x, 0]; + var raw1 = Pixels[idx]; return new Vector4(raw1, raw1, raw1, 255) / 255.0f; case 2: - var raw2 = Pixels[layer, y, x, 0] + (Pixels[layer, y, x, 1] << 8); + var raw2 = Pixels[idx] + (Pixels[idx + 1] << 8); return new Vector4(raw2 & 31, (raw2 >> 5) & 31, (raw2 >> 10) & 31, 31) / 31.0f; case 4: - // 4bpp stored as BGRA - return new Vector4(Pixels[layer, y, x, 2], Pixels[layer, y, x, 1], Pixels[layer, y, x, 0], Pixels[layer, y, x, 3]) / 255.0f; + return new Vector4(Pixels[idx + 2], Pixels[idx + 1], Pixels[idx], Pixels[idx + 3]) / 255.0f; default: return Vector4.Zero; } diff --git a/project/code/TMV/Mission.cs b/project/code/TMV/Mission.cs index 0345b31..0fc508a 100644 --- a/project/code/TMV/Mission.cs +++ b/project/code/TMV/Mission.cs @@ -299,9 +299,9 @@ public partial class Mission : Node3D if (info.cellIndex >= cells.Length) GD.Print($"CellIndex too big: {info.cellIndex}/{cells.Length}"); if (info.lightmapIndex >= cells[info.cellIndex].Lightmaps.Length) GD.Print($"LightmapIndex too big: {info.lightmapIndex}/{cells[info.cellIndex].Lightmaps.Length}"); var lightmap = cells[info.cellIndex].Lightmaps[info.lightmapIndex]; - var layers = (uint)lightmap.Pixels.GetLength(0); - var height = (uint)lightmap.Pixels.GetLength(1); - var width = (uint)lightmap.Pixels.GetLength(2); + var layers = (uint)lightmap.Layers; + var height = (uint)lightmap.Height; + var width = (uint)lightmap.Width; for (uint y = 0; y < height; y++) { for (uint x = 0; x < width; x++)