1 module voxd.rawvox; 2 3 import std.range, 4 std.file, 5 std.array, 6 std.string; 7 8 import voxd.utils; 9 10 /// Supports the VOX format used by the Build engine. 11 /// It is just a raw bitmap of 8-bit values. 12 13 /// Decodes a VOX file. 14 /// Throws: VoxdException on error. 15 VOX decodeRawVOXFromFile(string filepath) 16 { 17 auto bytes = cast(ubyte[]) std.file.read(filepath); 18 return decodeRawVOXFromMemory(bytes); 19 } 20 21 /// Decodes a VOX. 22 /// Throws: VoxdException on error. 23 VOX decodeRawVOXFromMemory(ubyte[] input) 24 { 25 26 // check header 27 int width = popLE!int(input); 28 int height = popLE!int(input); 29 int depth = popLE!int(input); 30 31 if (width < 0 || height < 0 || depth < 0) 32 throw new VoxdException("Strange value for dimensions, probably not such a VOX file"); 33 34 ubyte[] indices; 35 indices.length = width * height * depth; 36 for (size_t i = 0; i < indices.length; ++i) 37 { 38 indices[i] = popUbyte(input); 39 } 40 41 struct PalColor 42 { 43 ubyte r, g, b; 44 } 45 46 PalColor[256] palette; 47 for (int i = 0; i < 256; i++) 48 { 49 palette[i].r = popUbyte(input); 50 palette[i].g = popUbyte(input); 51 palette[i].b = popUbyte(input); 52 } 53 54 VOX result; 55 result.width = width; 56 result.height = height; 57 result.depth = depth; 58 result.voxels.length = width * height * depth; 59 60 for(int x = 0; x < width; x++) 61 for(int y = 0; y < height; y++) 62 for(int z = 0; z < depth; z++) 63 { 64 int position = z + y * depth + x * width * height; 65 auto color = palette[indices[position]]; 66 result.voxel(x, y, z) = VoxColor(color.tupleof, 255); 67 } 68 69 return result; 70 } 71