Ejemplo n.º 1
0
        public static void Load(WadFile wad, Stream stream)
        {
            if (wad == null)
            {
                throw new ArgumentNullException("wad");
            }
            if (stream == null)
            {
                throw new ArgumentOutOfRangeException("stream");
            }

            var reader = new BinaryReader(stream);

            var startOffset = stream.Position;// Position of start in stream (current - version)

            // Validate version
            uint version = reader.ReadUInt32();

            if (version != Version)
            {
                throw new BspLib.Wad.Exceptions.WadVersionNotSupportedException(version);
            }

            // Header
            int num    = reader.ReadInt32(); // Number of entries, not textures
            int offset = reader.ReadInt32();

            var entries = new List <WadEntry>();

            // Offset of entries
            // Often bedore end of file
            stream.Position = offset + startOffset;
            for (int i = 0; i < num; i++)
            {
                var entry = WadEntry.Read(reader);
                // Is a texture
                if (entry.Type == WadEntry.TextureType)
                {
                    // Compressed
                    if (entry.Compressed)
                    {
                        // Could not find how it works (no documentation).
                        // In official github ( https://github.com/ValveSoftware/halflife/blob/5d761709a31ce1e71488f2668321de05f791b405/utils/common/wadlib.c on line 301 ):
                        //    // F I X M E: do compression
                        Console.Error.WriteLine("WadEntry ID={0}, Name='{1}' is compressed texture which is not supported. Skipping.", i, entry.Name_s);
                    }
                    // Not Compressed
                    else
                    {
                        entries.Add(entry);
                    }
                }
                // Not a texture
                else
                {
                    Console.Error.WriteLine("WadEntry ID={0}, Name='{1}' has unknown / unsupported type 0x{2:X2}.", i, entry.Name_s, entry.Type);
                }
            }

            // Load all textures
            for (int i = 0; i < entries.Count; i++)
            {
                var entry = entries[i];

                stream.Position = entry.PositionInFile + startOffset;

                var texture_info = TextureLumpInfo.Load(reader);
                var texture      = texture_info.LoadTexture(reader, entry.PositionInFile);

                wad.Textures.Add(texture);
            }
        }
Ejemplo n.º 2
0
        public static void Save(WadFile wad, Stream stream)
        {
            if (stream == null)
            {
                throw new ArgumentNullException(nameof(stream));
            }

            var writer = new BinaryWriter(stream);

            var startOffset = stream.Position;

            // Version
            writer.Write(Version);
            writer.Flush();

            // Header

            // Valid texture count (number of entries)
            writer.Write((int)wad.Textures.Count(t => t is Texture));
            // TextureLumpInfo offset position
            // Will be changed later
            var global_textureLumpInfo_offset_position = stream.Position;

            writer.Write((int)0);
            writer.Flush();

            List <int>    positions = new List <int>();
            List <char[]> names     = new List <char[]>();
            List <int>    sizes     = new List <int>();

            for (int i = 0; i < wad.Textures.Count; i++)
            {
                long position = stream.Position - startOffset;
                positions.Add((int)position);

                TextureByteIndexPaletteWithMipmaps texture;
                TextureLumpInfo textureLump;

                var t = wad.Textures[i];

                if (t is TextureByteIndexPalette)
                {
                    if (t is TextureByteIndexPaletteWithMipmaps)
                    {
                        texture = (TextureByteIndexPaletteWithMipmaps)t;
                    }
                    else
                    {
                        var tbip = (TextureByteIndexPalette)t;
                        texture = tbip.GenerateMipmaps(TextureLumpInfo.MipmapOffsetsLength);
                    }
                }
                else
                {
                    //throw new NotImplementedException("Textures without byte palette are not supported yet");
                    var tbip = TextureByteIndexPalette.CreateFromBitmap(t);
                    texture = tbip.GenerateMipmaps(TextureLumpInfo.MipmapOffsetsLength);
                }
                textureLump = new TextureLumpInfo(texture);

                textureLump.Save(writer);

                long length = stream.Position - position - startOffset;
                sizes.Add((int)length);
            }

            var global_wadEntry_position = stream.Position;

            stream.Position = global_textureLumpInfo_offset_position;
            writer.Write((int)(global_wadEntry_position - startOffset));
            writer.Flush();

            stream.Position = global_wadEntry_position;

            for (int i = 0; i < positions.Count; i++)
            {
                var position = positions[i];
                var name     = names[i];
                var size     = sizes[i];

                var entry = new WadEntry((int)(position - startOffset), size, WadEntry.TextureType, name);
                entry.Write(writer);
            }
        }